Por que não posso canalizar para o cd?

6

Por que não posso canalizar coisas para o cd?

Exemplo:

$ pwd >> ~/mloc
$ cd /
$ tail -n 1 ~/mloc | cd

cd falha. Se: cd $(tail -n 1 ~/mloc) , funciona.

Eu entendo que o último comando que escrevi funciona, mas não entendo por que não posso canalizar para o cd.

    
por morphheus 12.01.2014 / 02:11

2 respostas

9

Pipar para um processo envia dados para ele no lugar do que você digitaria após ter lançado o processo, não o que você digitaria como parte do comando que inicia o processo.

( cd também não é um processo, mas isso é menos importante, eu o abordo abaixo.)

Piping anexa a saída de um comando à entrada de outro comando . Considere:

foo | bar

Isso executa bar , executa foo e:

  • em vez de mostrar a saída de bar no terminal, ele direciona para foo como entrada.
  • em vez de levar entrada para foo do terminal , ele sai da saída de bar .

(Ambos os pontos realmente expressam a mesma coisa.)

Então, o que acontece quando você executa tail -n 1 ~/mloc | cd ?

  • Ele executa cd e, sempre que cd aceita entrada durante a execução, recebe essa entrada da saída de tail -n 1 ~/mloc .
  • cd nunca aceita entrada durante a execução.

Veja fluxos padrão (Wikipedia) para obter mais informações sobre o significado preciso de entrada e saída nesta resposta. (Aqui, por entrada, quero dizer "entrada padrão" e por saída quero dizer "saída padrão".)

Há também o problema de que cd não é, na verdade, um programa, mas um shell embutido, portanto, quando você executa cd , nenhum novo processo é iniciado. Mas isso não é realmente porque o que você está tentando não funciona, porque:

  • O uso de pipes para passar argumentos de linha de comando, como você está tentando, nunca funcionará em nenhum programa.
  • Não há razão para que um shell não possa ser escrito para acomodar pipes a um shell embutido, considerando que eles acomodam pipes de shell builtins.

    Note que, às vezes, quando você usa um shell embutido como se fosse um programa real, o que acontece é que o programa real com o mesmo nome é executado. Mas não há programa separado para cd e podemos canalizar de cd ; por exemplo, execute cd blah 2>&1 | less ; Se blah não existir ou não for um diretório, você poderá visualizar o erro em less .

Por fim, considere o que é diferente sobre cd $(tail -n 1 ~/mloc) . Este comando:

  • Executa tail -n 1 ~/mloc e captura sua saída.
  • Em vez de exibir a saída, cria um comando que consiste em anexá-la a cd .
  • Executa esse comando.
por Eliah Kagan 12.01.2014 / 02:26
0

A resposta curta é: o cd não funciona assim.

link

A resposta mais longa é que, no bash, os comandos em um pipeline são executados em um subshell. Como o cd é um shell embutido, ele afeta apenas o shell em que ele é executado. Se você estiver dentro de um subshell, o efeito desaparecerá quando a subshell sair.

    
por glenn jackman 12.01.2014 / 02:16

Tags