Supposons que je veuille supprimer tous les fichiers d'un répertoire à l'exception d'un nommé "notes.txt". Je ferais cela avec le pipeline, ls | grep -v "notes.txt" | xargs rm
. Pourquoi ai-je besoin de xargs si la sortie du second canal est l'entrée que rm doit utiliser?
Par souci de comparaison, le pipeline echo "#include <knowledge.h>" | cat > foo.c
insère le texte en écho dans le fichier sans utiliser de xargs. Quelle est la différence entre ces deux pipelines?
ls | grep -v "notes.txt" | xargs rm
pour supprimer tout sauf pournotes.txt
, ou en général, ne jamais analyser lals
sortie . Votre commande serait interrompue si un seul fichier contenait un espace, par exemple. La manière la plus sûre seraitrm !(notes.txt)
dans Bash (avecshopt -s extglob
set), ourm ^notes.txt
dans Zsh (avecEXTENDED_GLOB
) etc.find . -maxdepth 1 -mindepth 1 -print0 | xargs -0
au lieu dels | xargs
:-)Réponses:
Vous confondez deux types d'entrée très différents: STDIN et arguments. Les arguments sont une liste de chaînes fournies à la commande au démarrage, généralement en les spécifiant après le nom de la commande (par exemple,
echo these are some arguments
ourm file1 file2
). STDIN, d'autre part, est un flux d'octets (parfois du texte, parfois non) que la commande peut (éventuellement) lire après son démarrage. Voici quelques exemples (notez que celacat
peut prendre des arguments ou STDIN, mais cela fait des choses différentes avec eux):xargs
peut être considéré comme la conversion d'une entrée de style STDIN en arguments:echo
fait en fait plus ou moins l'inverse: il convertit ses arguments en STDOUT (qui peut être canalisé vers le STDIN d'une autre commande):la source
cat
prend des entrées deSTDIN
etrm
ne le fait pas. Pour ces commandes, vous devezxargs
parcourirSTDIN
ligne par ligne et exécuter les commandes avec les paramètres de ligne de commande.la source