puddletag - Linux ¿por qué no puedo conectar el resultado de la búsqueda a rm?
mp3tag ubuntu (4)
Para ampliar la respuesta de @Alex Gitelman: sí, hay una diferencia entre "entrada estándar" y la línea de comando.
Cuando escribe rm a.txt b.txt c.txt
, los archivos que enumera después de rm
se conocen como argumentos y están disponibles para rm a través de una variable especial (llamada argv
internamente). La entrada estándar, por otro lado, se ve en un programa Unix como un archivo llamado stdin
. Un programa puede leer datos de este "archivo" tal como lo haría si abre un archivo normal en el disco y lee de eso.
rm
, como muchos otros programas, toma sus argumentos de la línea de comando pero ignora la entrada estándar. Puedes canalizar cualquier cosa que te guste; simplemente arrojará esos datos. Ahí es donde xargs
es útil. Lee las líneas en la entrada estándar y las convierte en argumentos de línea de comandos, por lo que puede canalizar los datos a la línea de comando de otro programa. Es un buen truco.
Por ejemplo:
find . -name ".txt" | xargs rm
find . -name ".txt" | grep "foo" | xargs rm
Tenga en cuenta que esto funcionará incorrectamente si hay algún nombre de archivo que contenga líneas nuevas o espacios. Para tratar con nombres de archivos que contienen nuevas líneas o espacios, debe usar en su lugar:
find . -name ".txt" -print0 | xargs -0 rm
Esto indicará a find
que rescinda los resultados con un carácter nulo en lugar de una nueva línea. Sin embargo, grep
no funcionará como antes. En cambio, usa esto:
find . -name ".txt" | grep "foo" | tr "/n" "/0" | xargs -0 rm
Este tiempo tr
se usa para convertir todas las líneas nuevas en caracteres nulos.
lo siento si esta es una pregunta noobie pero no puedo encontrar una buena respuesta.
Para encontrar, elimina algo que pueda usar
find . -name ".txt" -exec rm "{}" /;
Pero ¿por qué no puedo simplemente canalizar los resultados a rm como
find . -name ".txt" | rm
como si fuera un tubo para grep
find . -name ".txt" | grep a
He leído en alguna parte que rm no toma entrada de stdin y, por lo tanto, no puedo canalizarlo, pero ¿qué significa eso? Cuando escribo rm a.txt lee de la entrada estándar al igual que grep ¿verdad? O hay una diferencia entre stdin y la línea de comandos. ¡Ayuda!
Pipe envía la salida del primer comando a la entrada estándar del segundo. rm
no acepta la entrada estándar por lo que no puede conectarse a ella. Puede usar xargs
para lograr el mismo efecto. Puede encontrar ejemplos de xargs
específicamente para su caso en la página man para xargs .
Una alternativa sin usar tuberías:
xargs rm -f <<< $(find . -name ".txt")
"¿Por qué no puedo encontrar el resultado de la tubería a la rm?"
Cuando canaliza algo a un programa, la tubería reemplaza la entrada del teclado. Tenga esto en cuenta y pregúntese la siguiente pregunta: ¿Qué haría con un teclado? ¿Eliminar las teclas presionadas? (un poco tonto de hecho) ¿Aceptar control interactivo? ( rm
no es interactivo, excepto algunas veces cuando necesita confirmación, que de hecho puede ser dada por una tubería).
Como cuestión de hecho, cuando rm
ya se está ejecutando, no puede escribir comandos para permitir que elimine archivos ... por lo que tampoco puede hacer eso con un conducto.
Si tiene en cuenta que una tubería reemplaza la combinación de teclado / pantalla, las cosas aparecerán inmediatamente más lógicas.
Ahora al revés. Puede canalizar un flujo de datos en grep
. ¿Significa eso que puedes dejar que grep lea las teclas del teclado como datos de entrada?
¡SÍ! Eso es realmente lo que hace de forma nativa (sin tuberías).
(Por favor, tenga en cuenta que no puede canalizar ni escribir el argumento de búsqueda en grep
)
Entonces ahora sabes por qué no puedes canalizar a rm y esperar que funcione como un argumento de línea de comando.
tl; dr:
Anatomía de un programa según la filosofía de UNIX:
archivar, archivar, teclado, eliminar pantalla. -> Pipe solo reemplaza el teclado y la pantalla.