Czy można wydrukować rozszerzenie powłoki?

18

Wiem, że istnieje określony zestaw reguł, które rozszerzają polecenia wpisywane przez użytkownika. (porozmawiajmy o powłoce bash).

Czy po rozwinięciu powłoki można wydrukować polecenie w formie? Wydaje się, że dobrym narzędziem jest nauka i sprawdzanie, jak powłoka rozwija znaki specjalne.

na przykład

$ echo *

{all the filenames in current dir}

Chcę wydrukować rozwinięte polecenie, które jest następującą linią:

echo {all the filenames in .}
Weishi Zeng
źródło

Odpowiedzi:

13

Po prostu użyj echo... umieść go przed poleceniem, które chcesz rozwinąć. Używam tego dość często.

$ ls
one.txt
two.txt
three.dat
$ echo rm *.txt
rm one.txt two.txt
$ rm *.txt

Możesz użyć Homei, Delaby szybko dodać / usunąć poprzednie echo.

EDIT
Jak zauważył w komentarzach, to nie będzie działać, jeśli polecenie to nie tylko proste polecenia (jak gdyby to forpętla, wykorzystuje rurę |, lub &&czy cokolwiek innego w tym stylu).

BenjiWiebe
źródło
1
To właśnie robię podczas testowania skryptu
Barmar
Na to nadal wpływ mają inne tokeny powłoki echo cat * | someprogram, które nie robią tego, co myślisz na podstawie tej odpowiedzi.
Kroltan
13

Możesz użyć set -x.

Rozważmy na przykład skrypt:

$ cat script.sh
set -x
echo *

Po uruchomieniu wyświetla rozwiniętą echoinstrukcję przed jej wykonaniem:

$ bash script.sh
+ echo file1 file2 file3 script.sh
file1 file2 file3 script.sh

I, jak zauważa Kundor, działa to również interaktywnie w wierszu poleceń:

$ set -x
+ set -x
$ echo *
+ echo file1 file2 file3 script.sh
file1 file2 file3 script.sh

Dokumentacja

man bashwyjaśnia, co set -xrobi w następujący sposób:

Po rozwinięciu każdego prostego polecenia dla polecenia, przypadku, polecenia wyboru lub arytmetyki dla polecenia wyświetl rozwiniętą wartość PS4, a następnie polecenie i jego rozwinięte argumenty lub powiązaną listę słów.

Domyślną wartością PS4jest, jak pokazano powyżej, znak plus, po którym następuje spacja.

John1024
źródło
2
I działa również dobrze w interaktywnej powłoce (której, jak sądzę, szuka OP).
Nick Matteo
7

W przypadku interaktywnej powłoki naciśnięcie, Ctrl+xa następnie *wpisanie wzorca globu spowoduje edycję linii poleceń z rozwiniętym wzorcem globu. Ze strony podręcznika użytkownika bash:

glob-expand-word ( C-x *)

Słowo przed punktem jest traktowane jako wzorzec interpretacji nazwy ścieżki i wstawiana jest lista pasujących nazw plików, zastępując słowo. Jeśli podano argument numeryczny, przed rozwinięciem nazwy ścieżki dodawana jest gwiazdka.

Możesz być także zainteresowany rozszerzeniami glob-list ( Ctrl+x, g).

jamesdlin
źródło
Używam bash z Mac OS. Próbowałem ctrl + x, polecenie + x. Nie jestem pewien, czy dokonuje edycji wiersza poleceń. czy mógłbyś rozwinąć więcej?
Weishi Zeng
@WeishiZeng Nie wiem, dlaczego to nie działa dla ciebie. Czy nacisnąłeś Ctrl+x, *zaraz po wpisaniu echo *i przed naciśnięciem klawisza Enter? Jeśli nadal nie działa, możesz zmodyfikować ~/.inputrcglob-expand-word i powiązać go z czymś innym.
jamesdlin
contrl + x przesuwa kursor do słowa echo, ale niczego nie edytuje. „Ctrl + x ”, co to znaczy? (czy to ctrl + x LUB ctrl + ??) * jest na Shift, więc muszę też nacisnąć Shift, aby uzyskać *, prawda?
Weishi Zeng
W prawo, naciśnij, Ctrl+xa następnie Shift+8. Możesz spróbować sprawdzić, czy Ctrl+x, gdziała, lub, jak powiedziałem wcześniej, przypisz własny klucz do .inputrcpliku.
jamesdlin
1

Jeśli chcesz zobaczyć, jak argumenty są rozwijane lub tokenizowane, możesz użyć programu lub skryptu, który wypisuje swoje argumenty. Oto jedna implementacja w bash:

#!/bin/bash

for (( i = 0; i <= $#; ++i )); do
    printf 'argv[%d] = %s\n' $i "${!i}"
done

Zakładając, że umieścisz to w pliku o nazwie printargs.sh(i sprawisz, że będzie wykonywalny), otrzymasz wynik w ten sposób

$ ./printargs.sh a{1..3}b
argv[0] = ./printargs.sh
argv[1] = a1b
argv[2] = a2b
argv[3] = a3b
jjlin
źródło