Un de mes amis m'a dit que je pouvais utiliser l'astuce ci-dessous pour retirer une paire de crochets.
Placez le curseur à l'intérieur de la paire de crochets que vous souhaitez supprimer.
y i {pour tirer le texte entre accolades, v a {puis collez p.
Cela fonctionne bien comme:
for(int i = 0; i < s.length(); i++) {
int index = s[i] - c;
if(root->next[index] == NULL)
root->next[index] = new TrieNode;
root = root->next[index];
}
Après avoir exécuté la commande:
for(int i = 0; i < s.length(); i++)
int index = s[i] - c;
if(root->next[index] == NULL)
root->next[index] = new TrieNode;
root = root->next[index];
jusqu'à ce que je rencontre cette situation (l'espace avant le premier crochet est manquant).
for(int i = 0; i < s.length(); i++){
int index = s[i] - c;
if(root->next[index] == NULL)
root->next[index] = new TrieNode;
root = root->next[index];
}
Après avoir exécuté ces commandes, le bloc de texte devient
for(int i = 0; i < s.length(); i++
int index = s[i] - c;
if(root->next[index] == NULL)
root->next[index] = new TrieNode;
root = root->next[index];
)
La zone que je sélectionne en mode visuel semble bonne, mais pourquoi les parenthèses diminuent-elles?
return -1;
vient. Pourriez-vous également préciser où vous placez votre curseur avant d'exécuter chaque séquence de touches?yi{
tire entre les accolades etvap
sélectionne visuellement le paragraphe (le texte entier dans ce cas) mais je ne vois pas du tout comment cela change le texte. Êtes-vous sûr de ne pas faireyi{
+va{
+p
?yi{
+va{
+p
sur votre texte dans une session propre (pas de vimrc,-u NONE
) et cela reproduit votre résultat. Je ne sais pas pourquoi, par exemple,p
et lesP
deux donnent ce résultat, malgréi{
et sea{
déplaçant dans le sens des caractères. Il serait utile que vous puissiez a) donner un exemple de texte sur lequel votre technique fonctionne et b) confirmer où se produit le «changement» dans votre technique. @Ben indique une bonne solution de contournement dans sa réponse (j'utilise ce plugin) mais cela ne me dérangerait pas d'apprendre pourquoi cela se produit en premier lieu.Réponses:
Installez le plug - in « surround » . Ensuite, vous pouvez simplement faire d s B .
Depuis la page du projet:
La commande
ds
suivie de tout objet texte (B
dans ce cas, pour "Bloquer", comme dans l' objet texteaB
ouiB
) supprimera les caractères environnants qui définissent l'objet texte. Ainsi, d s B dans votre cas, accomplit ce que vous vouliez.D'autres commandes incluent c s B b, si vous souhaitez changer l'entourage
{...}
en(...)
, ou y s {tout mouvement de curseur ou objet texte} B pour ajouter un entourage{...}
au texte sélectionné par le curseur.Voir la page du plugin et la documentation pour plus de détails.
la source
Sommaire
C'est un bug et il y a un patch (743). Le bogue affecte à la fois vos exemples, mais vous ne le voyez pas dans un cas parce que le personnage qui est déplacé vers le bas est un (espace blanc). La solution consiste à installer le correctif, mais il existe également de nombreuses solutions de contournement ou méthodes alternatives, non affectées par le bogue.
L'insecte
Je ne le comprends pas entièrement, mais voici vers une explication, si quelqu'un est intéressé.
Le comportement que vous voyez est dû à un bogue mentionné par Yukihiro Nakadaira sur vim_dev et son correctif est publié en 7.4.743: "p" en mode visuel provoque un fractionnement de ligne inattendu .
Le mode visuel put (
:help v_p
) est censé remplacer le texte sélectionné visuellement par le texte d'un registre. Le bogue se produit lorsque a) le registre est de type ligne (:help linewise-register
) mais la sélection visuelle est de type caractère et b) la sélection visuelle se termine à la dernière colonne d'une ligne. Dans votre cas, si vous tirez sur le bloc intérieur puis sélectionnez visuellement un bloc et collez, le registre tiré sera dans le sens des lignes et la sélection visuelle sera dans le sens des caractères. Nous pouvons extraire le bloc interne et un bloc aux registres nommés et inspecter:Sur
Nous faisons
qui montre
et
Pour remplacer une sélection visuelle par caractère par un registre par ligne, les lignes qui contiennent le début et la fin de la sélection visuelle doivent être divisées en deux, afin que le texte puisse être inséré entre les deux. Cela fonctionne généralement très bien:
Exécuter vim as
vim -u NONE -U NONE
et taper( a )
résulte en
et ( b )
dans
Mais lorsque la sélection visuelle par caractère se termine à la dernière colonne d'une ligne (et n'inclut pas la nouvelle ligne
/n
/^J
), quelque chose ne va pas. Cela a à voir avec la position du curseur, qui est soudainement décalée de -1 et doit être spécialement incrémentée, ce que fait le patch. Comparez ( a ) avec la commande<Esc>ggYjllvp
, c'est-à-dire la même commande, sauf déplacez une colonne de plus vers la droite pour que le curseur se trouve sur le dernier "b" de la ligne. Le résultat est le même qu'avant!Prenez maintenant le texte suivant:
Avec le curseur sur la deuxième ligne, votre travail
yi{va{p
fonctionne très bien et donneLe registre yank est toujours en ligne et la sélection visuelle en caractères, mais la sélection visuelle ne se termine plus dans la dernière colonne, et tout va bien.
Exemples de textes de la question
Pour les deux exemples de texte, où la seule différence est un espace vide entre la fermeture des parenthèses et l'ouverture du crochet entre parenthèses dans la première ligne, il peut sembler que votre commande se comporte différemment, mais ce n'est vraiment pas le cas. Dans le premier cas, celui qui semble réussi, il devrait y avoir un espace de fin sur la première ligne une fois les crochets supprimés. Cet espace de fin est à la place sur la dernière ligne. Avec
yi{va{p
devient
juste comme
devient
Solutions
La solution serait d'installer le correctif, mais il existe de nombreuses autres façons de supprimer les supports environnants qui ne souffrent pas du bogue. La meilleure solution de contournement est la réponse @Gilles mais la plus simple peut être de sélectionner visuellement avant de tirer, pour garder le registre dans le sens des caractères.
Le plugin surround de Tim Pope est excellent, mais (au moins pour moi) il fait plus que supprimer les crochets: il joint la deuxième ligne à la première, il supprime l'indentation et il déplace le curseur au début de la première ligne. Cela laisse un nettoyage non trivial à faire. Ingo Karkat et Luc Hermitte ont des plugins qui traitent des registres et du collage (je suis sûr qu'il y en a beaucoup d'autres) et qui devraient pouvoir le faire. Je ne les connais pas très bien, mais je pense qu'avec les crochets lh, vous pouvez faire
<M-b>x
pour supprimer les crochets environnants et pour des mises plus puissantes (en particulier en mode visuel), vous pouvez regarder ReplaceWithRegister et UnconditionalPaste .La meilleure façon est celle donnée dans la réponse @Gilles,
[{x]}x
. Il est rapide, gère bien les blocs imbriqués et ne joint pas les lignes de manière inappropriée ou ne joue pas avec l'indentation. S'il y a un espace blanc avant le crochet d'ouverture, vous pouvez facilement ajouter unx
à la commande pour le supprimer:[{xx]}x
Autres commandes vanilla
Encore une fois, la commande la plus appropriée à laquelle je peux penser est celle de la réponse de @Gilles,
[{x]}x
ou[{xx]}x
, mais voici deux alternatives spécifiquement à la lumière de ce bogue.Yank caractère
Étant donné que le bogue se produit uniquement pour le registre de mise en ligne visuel mis sur la sélection de caractère, et comme il n'est qu'accidentel de votre yank de bloc interne qu'il soit en ligne, vous pouvez choisir de le tirer à la place. Un moyen facile est de choisir visuellement le bloc interne avant le collant, et de vous assurer que la sélection visuelle est characterwise (utilisation
v
nonV
):vi{yva{p
. Cela peut être le moyen le plus simple car il est très similaire à la façon dont vous effectuez actuellement l'opération.Ne pas utiliser de put visuel
D'autres commandes, comme changer et supprimer, ne sont pas affectées par ce bogue. Vous pouvez tirer comme auparavant, mais ensuite supprimer un bloc dans le registre de trou noir (
:help quote_
) et le mettre, ou supprimer un bloc et le mettre du registre 0 (:help quote0
):yi{"_da{p
ouyi{da{"0p
Généralité
Enfin, il existe des moyens similaires à la réponse @Gilles - déplacer au début d'un bloc, supprimer le caractère, déplacer à la fin d'un bloc, supprimer le caractère - mais qui sont plus génériques. La seule raison de les utiliser serait si le "bloc" que vous supprimez est excentrique et n'a pas de mouvements associés qui fonctionnent aussi bien que
[{
pour un bloc délimité par des accolades. Il y a une chance que le plugin vim-surround puisse bien gérer ces blocs excentriques, mais deux façons vanille seraient:help `<
) et supprimez le caractère.va{<Esc>x`<x
?{<CR>x/}<CR>x
Cela peut ne pas fonctionner correctement avec des blocs imbriqués.Nombre de caractères
la source
Puisque vous ne demandez pas que le curseur revienne à sa position d'origine,
[{x]}x
fait le travail. Il est long de 6 caractères avec deux pressions Shiftmais le principe est simple donc c'est facile à retenir.Si vous souhaitez revenir à la position d'origine, vous pouvez utiliser
[{x``]}x``
la source