Vím, že se to tu už pravděpodobně ptalo, ale na Googlu jsem to nenašel.
Dané
- Linuxové jádro
- Žádné konfigurace, které by změnily $HOME
- bash
Will ~ == $HOME
být pravda?
Přijatá odpověď:
Důležité je pochopit, že ~
Expanze je vlastnost shellu (některých shellů), není to magická postava, ale znamená váš domovský adresář, ať se používá kdekoli.
Je rozšířen (pomocí shellu, což je aplikace používaná k interpretaci příkazových řádků), jako $var
je za určitých podmínek rozšířen na svou hodnotu, když je použit v příkazovém řádku shellu před provedením příkazu.
Tato funkce se poprvé objevila v C-skořápce na konci 70. let (skořápka Bourne ji neměla, stejně jako její předchůdce, granát Thompson), byla později přidána ke skořápce Korn (novější shell postavený na Bourne shellu v 80. léta). Nakonec byl standardizován standardem POSIX a nyní je k dispozici ve většině shellů, včetně shellů jiných než POSIX, jako je fish
.
Vzhledem k tomu, že je to v prostředí shell tak rozšířené, některé aplikace mimo něj ho také rozpoznávají jako domovský adresář. To je případ mnoha aplikací v jejich konfiguračních souborech nebo jejich vlastních příkazový řádek (mutt
, slrn
, vim
…).
bash
konkrétně (což je shell projektu GNU a široce používaný v mnoha operačních systémech založených na Linuxu), když je vyvolán jako sh
, většinou se řídí pravidly POSIX o ~
expanze a v oblastech nespecifikovaných POSIXem se chová většinou jako shell Korn (jehož je částečným klonem).
Zatímco $var
je rozšířen na většině míst (kromě jednoduchých uvozovek), ~
expanze, která je dodatečným nápadem, je rozšířena pouze za několika specifických podmínek.
Je rozšířen, když je na vlastním argumentu v kontextu seznamu, v kontextech, kde se očekává řetězec.
Zde je několik příkladů rozšíření v bash
:
cmd arg ~ other arg
var=~
var=x:~:x
(požadováno POSIX, používá se pro proměnné jakoPATH
,MANPATH
…)for i in ~
[[ ~ = text ]]
[[ text = ~ ]]
(rozšíření~
je brán jako vzor v AT&Tksh
ale nebash
od 4.0).case ~ in ~) ...
${var#~}
(i když ne v některých jiných skořápkách)cmd foo=~
(i když ne při vyvolání jakosh
a pouze tehdy, když to, co je vlevo od=
má tvar neuvedenýchbash
název proměnné)cmd ~/x
(požadováno samozřejmě POSIX)cmd ~:x
(ale nex:~:x
nebox-~-x
)a[~]=foo; echo "${a[~]} $((a[~]))"
(ne v některých jiných skořápkách)
Zde je několik příkladů, kdy není rozšířen:
echo "~" '~'
echo [email protected] ~~
(Všimněte si také, že~u
je určen k rozšíření do domovského adresáře uživateleu
).echo @~
(( HOME == ~ ))
,$(( var + ~ ))
- pomocí
extglob
:case $var in @(~|other))...
(ačkolicase $var in ~|other)
je v pořádku). ./configure --prefix=~
(jako--prefix
není platný název proměnné)cmd "foo"=~
(vbash
, kvůli uvozovkám).- při vyvolání jako
sh
:export "foo"=~
,env JAVA_HOME=~ cmd
…
Pokud jde o to, na co se rozvine:~
sám expanduje na obsah HOME
proměnná, nebo když není nastavena, do domovského adresáře aktuálního uživatele v databázi účtů (jako rozšíření, protože POSIX ponechává toto chování nedefinované).
Je třeba poznamenat, že v ksh88 a bash
verze před 4.0 podstoupila expanze tildy globbing (generování názvu souboru) v kontextu seznamu:
$ bash -c 'echo "$HOME"'
/home/***stephane***
$ bash -c 'echo ~'
/home/***stephane*** /home/stephane
$ bash -c 'echo "~"'
~
V běžných případech by to neměl být problém.
Všimněte si, že protože je rozbalený, platí stejné varování jako u jiných forem rozšíření.
cd ~
Nefunguje, pokud je $HOME
začíná -
nebo obsahuje ..
komponenty. Takže, i když je velmi nepravděpodobné, že se to někdy změní, přísně vzato, jeden by měl napsat:
cd -P -- ~
Nebo dokonce:
case ~ in
(/*) cd -P ~;;
(*) d=~; cd -P "./$d";;
esac
(pro pokrytí hodnot $HOME
jako -
, +2
…) nebo jednoduše:
cd
(jako cd
přenese vás do vašeho domovského adresáře bez jakéhokoli argumentu)
Jiné shelly mají pokročilejší ~
rozšíření. Například v zsh
, máme:
~4
,~-
,~-2
(s dokončením) slouží k rozšíření adresářů ve vašem zásobníku adresářů (místa, která jstecd
do předtím).- dynamické pojmenované adresáře . Můžete definovat svůj vlastní mechanismus a rozhodnout, jak
~something
se rozšiřuje.