Jak szybko zmienić pierwsze słowo w poleceniu Bash?

44

Chciałbym nieco poprawić przepływ pracy w Bash i zdaję sobie sprawę, że często chcę wykonać to samo polecenie w innym pliku wykonywalnym.

Kilka przykładów:

Git (gdzie chciałbym szybko zmienić drugie słowo):

git diff     foo/bar.c
git checkout foo/bar.c

Cat / rm (gdzie należy zmienić tylko pierwsze słowo):

cat foo/is/a/very/long/path/to/bar.c
rm  foo/is/a/very/long/path/to/bar.c

Wiem, że mogę trafić Ctrl+ anastępnie Delusunąć pierwsze słowo, ale zastanawiam się, czy istnieje szybszy sposób to zrobić.

nowox
źródło
Szczerze mówiąc, myślę, że najbezpieczniej jest po prostu użyć Ctrl + a i usunąć. To zdecydowanie nie jest bardzo wolne.
agweber

Odpowiedzi:

56

!$ rozwija się do ostatniego słowa poprzedniego polecenia.

Więc możesz zrobić:

cat foo/is/a/very/long/path/to/bar.c

rm !$

lub:

git diff foo/bar.c

git checkout !$

Twoje przykłady powtarzały tylko ostatnie słowo, więc !$działało dobrze. Jeśli faktycznie miałeś wiele argumentów, które chciałeś powtórzyć, a chciałeś tylko zmienić pierwsze słowo, możesz użyć !*, który rozszerzy się na wszystkie słowa poprzedniego polecenia oprócz zera.

Zobacz sekcję „ROZSZERZENIE HISTORII” na bashstronie man. Jest tam duża elastyczność.

Spiff
źródło
16
Właściwe i właściwe. Chciałbym tylko ostrzec : gdy !$nie masz pełnej kontroli wzrokowej nad linią, którą biegniesz . Czasami może to być szkodliwe. Zwłaszcza jeśli popełnisz błąd w drukowaniu. To bierze z tego, historyco rozwinąć. Więc jeśli napiszesz ostatnie polecenie z pustą spacją na początku, prawdopodobnie to polecenie nie zakończy się w historii. Kiedy wykonasz nowe polecenie z !$powłoką, nie pobierze parametrów z ostatniego wpisanego wiersza poleceń, ale tylko z ostatniej historii. Tutaj te same słowa.
Hastur
1
@Hastur Możesz ustawić swoją powłokę, aby rozwijała historię na karcie lub po wejściu, aby zapobiec wypadkom.
slhck
2
@Hastur dlatego musisz dwukrotnie nacisnąć intro w zsh (bezwstydna promocja)
Braiam
@Hastur - Kiedy mam żadnych wątpliwości co do tego, co się wydarzy lub ja poniewczasie sprawę muszę zrobić coś innego zanim uruchomiony coś długo właśnie wpisany w, idę do początku wiersza i dodać #albo echo więc mogę zobacz i przejdzie do historii, dzięki czemu mogę go odzyskać i uruchomić ponownie bez wyłączającego prefiksu.
Joe
28

Ctrl+, aaby przejść do początku wiersza, a następnie Alt+, daby usunąć pierwsze słowo.

jjlin
źródło
9
Skrót usuwania słowa to tak naprawdę Meta + d, a Meta jest zwykle mapowana na Alt na komputerach z systemem Linux. Na platformach, na których tak nie jest, alternatywą dla uzyskania modyfikatora Meta jest użycie Escape jako prefiksu. Zobacz en.wikipedia.org/wiki/Meta_key
Gustavo Giráldez
2
@ GustavoGiráldez, jeśli chcesz zejść głęboko, Meta+Djest ważny tylko wtedy, gdy emacsjest włączony ( set -o emacsdomyślnie lub po prostu). Nie będzie działać w gorszym trybie edytora lub jeśli emacsjest wyłączony.
TC1
W wielu terminalach (ponieważ jest to rzecz terminalowa, a nie Bash), klawisz domowy przejdzie również na początek linii. Wiele laptopów mapuje Fn + klawisz lewej strony do klawisza głównego. Podobnie, klawisz zakończenia zwykle przechodzi na koniec linii. Muszę jeszcze użyć emulatora terminala, który nie obsługuje tych skrótów klawiszowych.
Kat
1
@Mike Z drugiej strony C-ai M-dsą znacznie szybsze w pisaniu, jeśli Twoje ręce są już w pozycji do pisania.
jjlin
@Mike To jest bash. Wpisz cati porównaj, co otrzymujesz, naciskając Dom ( ^[[Htutaj) i naciskając Ctrl + a ( ^A).
Jonas Schäfer
17

Nie jestem pewien, czy rzeczywiście byłoby to szybsze, czy nie, ale zobacz ten artykuł, szczególnie punkt # .3:

  1. Zamień ciąg z poprzedniego polecenia, używając ^ str1 ^ str2 ^

W poniższym przykładzie najpierw wykonaliśmy polecenie ls, aby zweryfikować plik. Później zdaliśmy sobie sprawę, że chcemy wyświetlić zawartość pliku. Zamiast ponownie wpisywać całą nazwę pliku, możemy po prostu zastąpić „ls” w poprzednim poleceniu „cat”, jak pokazano poniżej.

$ ls /etc/cron.daily/logrotate

$ ^ls^cat^
cat /etc/cron.daily/logrotate
Pingwin
źródło
15

Alt+.

Jeśli potrzebujesz tylko powtórzyć ostatnią część jednego z poprzednich poleceń, możesz użyć Alt+ ., który wklei ostatni argument pobrany z ostatniego wiersza historii.

Jeśli naciśniesz więcej niż jeden raz, zastąpi to, co właśnie wkleiłem ostatnim argumentem linii przed ...

Np. Jeśli ostatnie 2 polecenia to:

cat foo/is/a/very/long/path/to/bar.c
pico foo/is/a/very/long/path/to/SomeWhereElse.c

W powłoce piszę rmi naciskam Alt+ ., pojawi się:

rm foo/is/a/very/long/path/to/SomeWhereElse.c

jeśli nacisnę ponownie Alt+ ., zamiast tego pojawi się

rm foo/is/a/very/long/path/to/bar.c

i tak dalej...

Hastur
źródło
Nie wiem, dlaczego, ale to nie działa na mojej konsoli Mac.
lulalala
Oto skróty klawiaturowe , o których wiadomo, że działają bash. BTW Czy na pewno używasz bash jako powłoki ?
Hastur
1
To chyba Mac. Kiedy piszę, że dostaję
lulalala
12

Oprócz odpowiedzi na @jjlin mogą Cię zainteresować następujące wskazówki:

  • Ctrl+ wusuwa słowo po lewej stronie
  • Ctrl+ kusuwa kursor do końca wiersza poleceń
  • Ctrl+ uusuwa kursor z początku wiersza poleceń
  • Alt+ bprzesuwa kursor o jedno słowo do tyłu
  • Alt+ fprzesuwa kursor o jedno słowo do przodu
  • $_ zawiera ostatni argument poprzedniego wiersza poleceń

Więcej informacji na ten temat znajduje się w sekcji „Nazwy poleceń Readline” na stronie bashpodręcznika.

na przykład:

cat foo/is/a/very/long/path/to/bar.c
rm $_
maiki
źródło
To miłe wskazówki, ale nie odpowiadają na pytanie.
slhck
@slhck IMHO robi, ponieważ tytuł pytania nie pasuje do podanych przykładów. Jeśli skupimy się na przykładach, tak jak ja, tytuł powinien brzmieć „Jak szybko zmienić słowo w poleceniu bash?” . Dlatego też moja odpowiedź brzmi „oprócz tej z @jjlin”. Ale myślę, że pytanie powinno zostać wyjaśnione.
maiki
OP zawsze chce usunąć (wymienić) pierwsze nsłowa w poleceniu, z n = 1pierwszym przykładem i n = 2drugim. Odpowiedź jjlin pokazuje, jak usunąć pierwsze słowo (i przez ponowne zastosowanie skrótu, usunąć do nsłów). Twoja odpowiedź zawiera kilka skrótów Bash (które są naprawdę przydatne), ale żaden z nich nie jest skutecznym sposobem na usunięcie pierwszych nsłów.
slhck
Hm, ponowne czytanie, $_parametr prawdopodobnie działałby, gdyby był tylko jeden argument (tj. Jeśli n = m - 1gdzie mjest całkowita liczba argumentów). Pozostała część skrótów nie ma jednak znaczenia dla pytania.
slhck
@slhck Aby się kłócić, przeczytałem pierwszy przykład jako „zamień drugie słowo” :-)
maiki,
8

Jeśli jesteś biegły w vi, możesz aktywować wiązania vi w bash (większość powłok?) Za pomocą polecenia set -o vi. Następnie możesz użyć normalnych klawiszy vi do edycji polecenia. W pierwszym przykładzie możesz ^wcwusunąć „diff”, a następnie zmienić go na kasę.

Być może nie warto uczyć się skrótów klawiszowych vi tylko do edycji wiersza poleceń, ale jeśli już je znasz, to fajny wzrost wydajności.

Chaosed0
źródło
Nauczyłem się na kornshell, tak set -o viteż żyłem! Robię to nawet w podpowiedziach bash.
bgStack15
bindkey -vdla zsh. Esc 0 c w
user530873,
6

Jest wiele sposobów na skórowanie tego kota!

Aby wymienić konkretny ciąg, ^old^new^extrazajmie swoje poprzednie polecenie, wymień oldsię newi załącza extra. Możesz przerwać tak wcześnie, jak chcesz; np. ^oldzastąpi oldpusty ciąg i doda pusty ciąg (zasadniczo usuwając oldi nie robiąc nic więcej).

1. ^diff^checkout
2. ^cat^rm

Szczególnie przydatny wariant tego:

for i in `seq 1 10`; do echo something complicated; done
# inspect the output to see if it looks right
^echo

Aby wymienić konkretne słowo, można użyć !m:n-pw odniesieniu do słów nprzez ppolecenia m(numery stosowanie negatywnych liczyć wstecz od bieżącego polecenia). Możesz pominąć -pczęść odnoszącą się do pojedynczego słowa i pominąć :m-pczęść odnoszącą się do całego polecenia. Szczególne formy !!dla !-1, !$dla ostatniego słowa poprzedniej komendy, a !*dla wszystkich argumentów (ale słowo 0) z poprzedniego polecenia są dość wygodne.

1. !!:0 checkout !!:2-
2. rm !*

Często używam obu; Zsh jest tutaj szczególnie przyjemny, ponieważ naciśnięcie klawisza spowoduje rozwinięcie tajemniczych rzeczy, aby upewnić się, że masz rację.

Istnieje również wiele sposobów na zrobienie tego za pomocą edycji linii. Przeczytaj o skrótach klawiszowych twojej powłoki.

Daniel Wagner
źródło
-2

Większość programów terminalowych obsługuje ...

  • Naciśnij <Up-Arrow>w razie potrzeby, aby ponownie wyświetlić jedną z poprzednich linii poleceń z historii.
    • Naciśnij <Down-Arrow>w razie potrzeby, aby przejść do następnej listy historii.
  • Naciśnij <Left-Arrow>w razie potrzeby, aby przesunąć kursor na koniec drugiego słowa.
  • Naciśnij <Backspace>w razie potrzeby, aby usunąć drugie słowo.
  • Wpisz zastępcze drugie słowo.
    • Naciśnij <Right-Arrow>/ <Left-Arrow>w razie potrzeby, aby zmienić położenie, aby uzyskać więcej zmian.
  • Naciśnij, <RETURN>aby wykonać polecenie

Jeśli żądany wiersz komend nie był aktualny, wykonaj wyszukiwanie wsteczne i <Ctrl-r>zgodnie z opisem w pytaniu ...
Czy istnieje sposób użycia ctrl-r po wpisaniu części polecenia w bash?
Następnie w razie potrzeby edytuj za pomocą klawiszy strzałek.

DocSalvager
źródło
-3

Co robię (Ubuntu / bash):

1) Arrow uphej, aby powrócić do poprzedniego polecenia
2) Homeklawisz, aby powrócić do początku
3) Zmodyfikuj polecenie w razie potrzeby.

Odporne na idiotyzm i szczególnie przydatne w przypadku poleceń wieloliniowych.

Vorac
źródło