C'est vraiment assez ingénieux. Décomposons-le. La ex
commande
g/^$/xyzzy
recherchera toutes les lignes vides et exécutera la xyzzy
commande (une ex
commande arbitraire ) sur chacune d'elles. Notez que ce xyzzy
n'est pas une vraie ex
commande, c'est seulement là en tant qu'espace réservé, selon le paragraphe suivant.
L'astuce ici est que la xyzzy
"commande" dans votre cas est encore une autre commande de recherche:
,/./-j
Le ,/./-
spécifie une plage. Il s'agit du formulaire <start>,<end>
et, comme il n'y a rien avant la virgule, il suppose que la ligne actuelle (celle où vous avez trouvé la ligne vierge) est le début.
Après la virgule est /./-
ce qui signifie rechercher le caractère suivant ( .
signifie n'importe quel caractère) puis sauvegarder une ligne ( /./-
est abrégé /./-1
car celui-ci est implicite si aucune valeur n'est donnée). Vous trouverez ce modèle .
sur la première ligne non vide suivant celle sur laquelle vous opérez.
En d'autres termes, la fin de la plage est la dernière ligne vierge après ou sur celle sur laquelle vous travaillez actuellement.
Ensuite, vous exécutez une jointure sur cette plage.
Si le début et la fin de la plage étaient égaux (une seule ligne vierge se trouvait dans la section), join ne fait rien. S'ils ne sont pas égaux, rejoindre les rejoindra tous.
C'est ainsi qu'il combine plusieurs lignes vides en une seule.
Regardons un exemple (les numéros de ligne sont pour explication seulement, ils ne sont pas dans le fichier réel):
1 Line 1
2
3 Line 3
4 Line 4
5
6
7
8
9 Line 9
La g/^$/
commande trouvera toutes les lignes vides et effectuera son opération sur elles (ce sont les lignes 2, 5, 6, 7 et 8).
Pour la ligne 2, ,/./-j
établira une plage de 2 à 2 (la suivante .
se trouve sur la ligne 3, puis soustrayez 1 pour obtenir 2). Une jointure sur la plage 2,2 ne fait rien.
Pour la ligne 5, ,/./-j
établira une plage de 5 à 8 (à côté .
de la ligne 9 puis soustrayez 1). Une jointure sur la plage 5,8 reliera toutes ces lignes ensemble.
L'opération n'est pas effectuée sur les lignes qui disparaissent dans le cadre d'une opération antérieure. En effet, cela n'aurait aucun sens de traiter les lignes qui ont été supprimées plus tôt dans le cycle.
En d'autres termes, étant donné que les lignes 6 à 8 sont supprimées (combinées avec la ligne 5), la commande globale ne les opère pas après cela.
Cela est basé sur le fait que la vim
documentation indique un algorithme à deux passes, un pour marquer les lignes, un pour effectuer l'opération.