Powtarzam wiele:
mkdir longtitleproject
cd longtitleproject
Czy można to zrobić w jednym wierszu bez powtarzania nazwy katalogu? Jestem tutaj na haju.
mkdir longtitleproject
następniecd !^
Powtarzam wiele:
mkdir longtitleproject
cd longtitleproject
Czy można to zrobić w jednym wierszu bez powtarzania nazwy katalogu? Jestem tutaj na haju.
mkdir longtitleproject
następniecd !^
Odpowiedzi:
Nie ma wbudowanego polecenia, ale możesz łatwo napisać funkcję, która wywołuje mkdir
wtedy cd
:
mkcd () {
mkdir "$1"
cd "$1"
}
Umieść ten kod w swoim ~/.bashrc
pliku (lub ~/.kshrc
dla użytkowników ksh lub ~/.zshrc
dla użytkowników zsh). Definiuje funkcję o nazwie mkcd
. "$1"
zostanie zastąpiony argumentem funkcji po uruchomieniu.
Ta prosta wersja ma kilka wad:
-p
opcję do mkdir
. (Może to być lub nie być pożądane, ponieważ zwiększa ryzyko, że literówka mkcd mydierctory/newsub
pozostanie niewykryta, np. Z przyjemnością utworzy mydierctory
i mydierctory/newsub
kiedy zamierzasz utworzyć newsub
wewnątrz istniejącej mydirectory
).-
ale nie tylko -
, wtedy mkdir
i cd
zinterpretuje go jako opcję. Jeśli tak -
, to cd
zinterpretuje to w znaczeniu $OLDPWD
. Jeśli po nim +
następuje 0 lub więcej cyfr, to cd
w zsh zinterpretuje to jako indeks na stosie katalogów. Możesz rozwiązać pierwszy problem, ale nie pozostałe dwa, przekazując --
przed argumentem. Możesz rozwiązać wszystkie te problemy, przygotowując ./
argument, jeśli jest to ścieżka względna.mkdir
nie następuje CDPATH
, ale cd
tak jest, więc jeśli ustawisz CDPATH
wartość, która nie zaczyna się od .
(co prawda nieco nietypowa konfiguracja), cd
możesz przenieść cię do innego katalogu niż właśnie utworzony. Przygotowanie ./
do ścieżek względnych naprawia to (powoduje CDPATH
zignorowanie).mkdir
nie powiedzie, próbuje się wykonać cd
. Poprawka: użyj, &&
aby rozdzielić dwa polecenia.Wciąż dość proste:
mkcd () {
case "$1" in /*) :;; *) set -- "./$1";; esac
mkdir -p "$1" && cd "$1"
}
Ta wersja wciąż ma potencjał, aby cd
przejść do innego katalogu niż ten, który mkdir
właśnie utworzono w jednym przypadku krawędzi: jeśli argument mkcd
zawiera ..
i przechodzi przez dowiązanie symboliczne. Na przykład, jeśli bieżący katalog jest /tmp/here
i mylink
jest dowiązaniem symbolicznym do /somewhere/else
, wówczas mkdir mylink/../foo
tworzy, /somewhere/else/foo
podczas gdy cd mylink/../foo
zmienia się w foo
. Nie wystarczy szukać dowiązań symbolicznych w argumencie, ponieważ powłoka śledzi również dowiązania symboliczne w swoim bieżącym katalogu, więc cd /tmp/mylink; mkdir ../foo; cd ../foo
nie zmienia się w nowy katalog ( /somewhere/else/foo
), ale w /tmp/foo
. Rozwiązaniem tego cd
problemu jest zezwolenie wbudowanemu na rozpoznanie wszystkich ..
komponentów ścieżki w pierwszej kolejności (nie ma sensu używać foo/..
iffoo
nie istnieje, więc mkdir
nigdy nie trzeba go widzieć ..
).
Dochodzimy do tej solidnej, choć nieco krwawej wersji:
mkcd () {
case "$1" in
*/..|*/../) cd -- "$1";; # that doesn't make any sense unless the directory already exists
/*/../*) (cd "${1%/../*}/.." && mkdir -p "./${1##*/../}") && cd -- "$1";;
/*) mkdir -p "$1" && cd "$1";;
*/../*) (cd "./${1%/../*}/.." && mkdir -p "./${1##*/../}") && cd "./$1";;
../*) (cd .. && mkdir -p "${1#.}") && cd "$1";;
*) mkdir -p "./$1" && cd "./$1";;
esac
}
(Ćwiczenie: dlaczego używam podpowłoki do pierwszego cd
połączenia?)
Jeśli mkdir zawiedzie, chcę mieć pewność, że nie zmieniłem bieżącego katalogu. Cofanie się za pomocą cd - lub $ OLDPWD nie jest wystarczająco dobre, jeśli powłoka nie ma uprawnień do przejścia do bieżącego katalogu. Również wywołanie cd aktualizuje OLDPWD, więc chcemy to zrobić tylko raz (lub przywrócić OLDPWD).
Istnieją również mniej wyspecjalizowane sposoby, aby nie musieć wpisywać słowa z poprzedniego wiersza:
cd
, a następnie Esc .(lub Alt+ .), aby wstawić ostatni argument z poprzedniego polecenia.cd !$
wykonuje cd
się na ostatnim argumencie poprzedniego polecenia.mkdir
na cd
.ksh
, a także działa w zsh
) dla „powtórz ostatnie słowo poprzedniego polecenia”. Używam tego dość często.
/a/b/..//
faktycznie działałoby, ale nie działało /a/b/../c
. Naprawiony. Zadałem to pytanie szerszej publiczności.
mkcd() { mkdir -p "$1" && cd "$1"; }
nie wydaje się być problemem w (moim przypadku) zsh. mkdir -p /var/tmp/somewhere/else /tmp/here; cd /tmp/here; ln -s /var/tmp/somewhere/else mylink; mkdir -p mylink/../foo && cd mylink/../foo; pwd
(obejmuje konfigurację i) wyświetla, /tmp/here/foo
co zostało utworzone (i czego się spodziewałem). bash
błędnie tworzy i zmienia się w /var/tmp/somewhere/foo
.
Jest to jedna linijka, której potrzebujesz. Nie jest wymagana żadna inna konfiguracja:
mkdir longtitleproject && cd $_
$_
Zmienna, w bash, jest ostatnim argumentem podane do poprzedniego polecenia. W takim przypadku nazwa właśnie utworzonego katalogu. Jak wyjaśniono w man bash
:
_ At shell startup, set to the absolute pathname used to invoke
the shell or shell script being executed as passed in the envi‐
ronment or argument list. Subsequently, expands to the last
argument to the previous command, after expansion. Also set to
the full pathname used to invoke each command executed and
placed in the environment exported to that command. When check‐
ing mail, this parameter holds the name of the mail file cur‐
rently being checked."$_" is the last argument of the previous command.
Służy cd $_
do pobierania ostatniego argumentu poprzedniego polecenia zamiast, cd !$
ponieważ cd !$
podaje ostatni argument poprzedniego polecenia w historii powłoki :
cd ~/
mkdir folder && cd !$
kończysz w domu (lub ~ /)
cd ~/
mkdir newfolder && cd $_
kończysz w nowym folderze pod domem !! (lub ~ / newfolder)
mkdir foo && cd foo
, co nie jest przydatne.
Nigdy nie przyszło mi do głowy, aby opisać to zachowanie, ponieważ wpisuję następujące informacje prawie co godzinę ...
$ mkdir someDirectory<ENTER>
$ cd !$
gdzie bash uprzejmie zastępuje !$
ostatnie słowo ostatniego wiersza; tzn. podana długa nazwa katalogu.
Ponadto uzupełnianie nazw plików jest Twoim przyjacielem w takich sytuacjach. Jeśli twój nowy katalog był jedynym plikiem w tym folderze, szybki podwójny plik TABda ci nowy katalog bez ponownego wchodzenia do niego.
Chociaż fajnie jest, że bash pozwala na tworzenie skryptów tak typowych zadań, jak inne odpowiedzi sugerują, myślę, że lepiej jest nauczyć się funkcji edycji wiersza poleceń, które bash ma do zaoferowania, aby podczas pracy na innym komputerze nie brakowało składni cukier dostarczany przez niestandardowe skrypty.
Zgodnie z Jakimi dostosowaniami dokonałeś się w swoim profilu powłoki, aby zwiększyć wydajność? , tak to robię:
# make a directory and cd to it
mcd()
{
test -d "$1" || mkdir "$1" && cd "$1"
}
oznacza to, że działa również, jeśli katalog już istnieje.
-p
Opcja mkdir będzie tłumić błędów.
mcd
polecenie? Który pakiet lub projekt udostępnia to polecenie?
Jeśli używasz Oh My Zsh, istnieje polecenie o nazwie take, które właśnie to robi. Wyglądałoby to mniej więcej tak.
take myfolder
Znalazłem to przypadkiem. Właśnie spojrzałem i jest wymieniony na tym cheatheat z wiki Oh My Zsh GitHub. Jest to dość przydatne polecenie i najwyraźniej bardzo łatwe do samodzielnego stworzenia.
take
:) Idealnie! btw - iTerm2 z Oh My Zsh. Istnieją tutaj 3 idealne odpowiedzi. Ten, autorstwa @ jesús-carrera i wybraną odpowiedź. Zależy od konfiguracji i preferencji.
Oto niewielki wariant, który warto wspomnieć:
function mkdir() {
local dir=$1
command mkdir "$dir" && cd "$dir"
}
Dodaj to do swojego, ~/.bash_profile
a będziesz mógł używać mkdir
jak zwykle (kiedy już to zrobisz source
), tyle że teraz uruchomi funkcję powyżej zamiast standardowego mkdir
polecenia.
Zauważ, że to nie sprawdza poprawności danych wejściowych zgodnie z zaakceptowaną odpowiedzią Gillesa , ale pokazuje, jak możesz (skutecznie) zastąpić wbudowane.
Z dokumentów (nieco parafrazując):
command mkdir [args]
działamkdir
zargs
ignorowaniem dowolnej funkcji powłoki o nazwiemkdir
. Wykonywane są tylko wbudowane polecenia powłoki lub polecenia znalezione podczas przeszukiwania ŚCIEŻKI. Jeśli jest nazwana funkcja powłokils
, uruchomieniecommand ls
w obrębie funkcji spowoduje wykonanie polecenia zewnętrznegols
zamiast wywoływania funkcji rekurencyjnie
Wierzę, że builtin
osiąga podobny wynik command
.
$dir
command
jako alternatywy.
Zrobiłem skrypt, który tworzy katalog, a następnie płyty CD, a następnie nadałem mu alias. A tutaj jest sedno, w którym to opisuję.
https://gist.github.com/rehnen/34236d6ff270ccaa74b6#mkdir-like-it-was-meant-to-be
Właśnie zautomatyzowałem powyższe odpowiedzi i utworzyłem skrypt wykonywalny jednorazowo:
fun='
mkcd ()
{
mkdir -p -- "$1" && cd -P -- "$1"
}'
echo "$fun" >> ~/.bashrc
Po prostu skopiuj to do nowego pliku mkcd.sh
i uruchom tylko raz w terminalu przez bash mkcd.sh
. Następnie uruchom, source ~/.bashrc
aby działał w bieżącej sesji.
Następnie możesz użyć mkcd some_dir
do utworzenia i przejścia bezpośrednio do tego katalogu.
~/.bashrc
pliku (z udzieloną już odpowiedzią)? A jak sugerujesz utworzenie tego mkcd.sh
skryptu? Może z redaktorem? To wygląda na więcej pracy niż tylko edycję ~/.bashrc
. Jakie to ma przewagę nad przyjętą odpowiedzią? ……………………………………………………………………… PS To się nie powiedzie z powodu cytowania problemów, które mówią mi, że nawet nie próbowałeś tego.
mcd
from unix.stackexchange.com/questions/6628/…