Sé que esto probablemente se haya preguntado antes, pero no pude encontrarlo con Google.
Dado
- Kernel de Linux
- No hay configuraciones que cambien $ HOME
- golpetazo
Será ~ == $HOME
verdad?
bash
shell
environment-variables
home
PythonNut
fuente
fuente
~
que será equivalente a$HOME
cualquier entorno POSIX; Pero podría estar equivocado.echo "~"
yecho "$HOME"
.~
o$HOME
. : P~
".) De todos modos, algo a tener en cuenta para el lector casual, como yo.Respuestas:
Lo que es importante entender es que la
~
expansión es una característica del shell (de algunos shells), no es un personaje mágico que significa su directorio de inicio donde sea que se use.Se expande (mediante el shell, que es una aplicación utilizada para interpretar líneas de comando), al igual que
$var
se expande a su valor en algunas condiciones cuando se usa en una línea de comando del shell antes de ejecutar el comando.Esa característica apareció por primera vez en el C-shell a fines de la década de 1970 (el shell Bourne no lo tenía, ni su predecesor, el shell Thompson), luego se agregó al shell Korn (un shell más nuevo construido sobre el shell Bourne en el 80s). Eventualmente fue estandarizado por POSIX y ahora está disponible en la mayoría de los shells, incluidos los que no son POSIX
fish
.Debido a su uso tan extendido en shells, algunas aplicaciones que no son de shell también lo reconocen como el directorio de inicio. Ese es el caso de muchas aplicaciones en sus archivos de configuración o de su propia línea de comandos (
mutt
,slrn
,vim
...).bash
específicamente (que es el shell del proyecto GNU y ampliamente utilizado en muchos sistemas operativos basados en Linux), cuando se invoca comosh
, en su mayoría sigue las reglas POSIX sobre~
expansión, y en áreas no especificadas por POSIX, se comporta principalmente como el shell Korn (de que es un clon parcial).Si bien
$var
se expande en la mayoría de los lugares (excepto dentro de comillas simples), la~
expansión, una idea de último momento solo se expande en unas pocas condiciones específicas.Se expande cuando está en su propio argumento en contextos de lista, en contextos donde se espera una cadena.
Aquí hay algunos ejemplos de dónde se expande
bash
:cmd arg ~ other arg
var=~
var=x:~:x
(requerido por POSIX, usado para variables comoPATH
,MANPATH
...)for i in ~
[[ ~ = text ]]
[[ text = ~ ]]
(la expansión de~
ser tomado como un patrón en AT&Tksh
pero nobash
desde 4.0).case ~ in ~) ...
${var#~}
(aunque no en otras conchas)cmd foo=~
(aunque no cuando se invoca comosh
, y solo cuando lo que está a la izquierda=
tiene la forma de unbash
nombre de variable sin comillas )cmd ~/x
(requerido por POSIX obviamente)cmd ~:x
(pero nox:~:x
ox-~-x
)a[~]=foo; echo "${a[~]} $((a[~]))"
(no en otras conchas)Aquí hay algunos ejemplos donde no se expande:
echo "~" '~'
echo ~@ ~~
(también tenga en cuenta que~u
está destinado a expandirse al directorio de inicio del usuariou
).echo @~
(( HOME == ~ ))
,$(( var + ~ ))
extglob
:case $var in @(~|other))...
(aunquecase $var in ~|other)
está bien)../configure --prefix=~
(como--prefix
no es un nombre de variable válido)cmd "foo"=~
(enbash
, debido a las comillas).sh
:export "foo"=~
,env JAVA_HOME=~ cmd
...En cuanto a lo que se expande:
~
solo se expande al contenido de laHOME
variable, o cuando no está configurado, al directorio de inicio del usuario actual en la base de datos de la cuenta (como una extensión ya que POSIX deja ese comportamiento indefinido).Cabe señalar que en ksh88 y
bash
versiones anteriores a la 4.0, la expansión de tilde experimentó un bloqueo (generación de nombre de archivo) en contextos de lista:Eso no debería ser un problema en los casos habituales.
Tenga en cuenta que debido a que está expandido, se aplica la misma advertencia que otras formas de expansión.
No funciona si
$HOME
comienza con-
o contiene..
componentes. Entonces, aunque es muy poco probable que alguna vez haga alguna diferencia, estrictamente hablando, uno debería escribir:O incluso:
(para cubrir valores de me
$HOME
gusta-
,+2
...) o simplemente:(como lo
cd
lleva a su directorio de inicio sin ningún argumento)Otros proyectiles tienen
~
expansiones más avanzadas . Por ejemplo, enzsh
, tenemos:~4
,~-
,~-2
(Con la terminación) que se utiliza para expandir los directorios en su pila de directorios (los lugares que hacd
de antes).~something
se está expandiendo.fuente
En cualquier versión de Bash en cualquier sistema, sí .
~
como un término en sí mismo se define para expandirse a:así que siempre será lo mismo que lo que sea
$HOME
para el shell actual. Hay varias otras expansiones de tilde, como el directorio de inicio de~user
foruser
, pero una sola sin comillas~
siempre se expandirá a"$HOME"
.Tenga en cuenta que el comportamiento de
~
y$HOME
puede ser diferente en algunos casos: en particular, si$HOME
contiene espacios (u otros IFS caracteres), luego$HOME
(sin comillas) se expandirá a varias palabras, mientras que~
es siempre una única palabra.~
se expande de manera equivalente a"$HOME"
(citado).Con respecto a su pregunta específica:
siempre es cierto, porque
[[
suprime la división de palabras.[[ ~ == $HOME ]
puede no serlo siHOME
tiene caracteres de coincidencia de patrones , pero[[ ~ == "$HOME" ]]
(es decir, entre comillas"$HOME"
) siempre es cierto. Usarlo entre paréntesis puede ser un error de sintaxis para valores deHOME
espacios o caracteres especiales. Para cualquier configuración de directorio de inicio sensible~
y"$HOME"
son iguales y se comparan como iguales.Stéphane Chazelas ha notado un caso en los comentarios donde
~
y$HOME
da diferentes valores: si ustedunset HOME
, cuando use~
Bash, lo llamarágetpwuid
para leer un valor de la base de datos de contraseñas. Este caso está excluido por su condición de no cambiar la configuración$HOME
, pero lo mencionaré aquí para completarlo.fuente
/bin/sh
puede que no seabash
. No estoy seguro de que lash
especificación de Posix diga sobre~
~
.~
no estaba en el shell Thomson o Bourne (que en su momento estaban disponibles como/bin/sh
). No está ni enrc
sus derivados (donde se usa para otra cosa)bash
, si noHOME
está configurado, se~
expande al directorio de inicio del usuario desde la base de datos passwd. Entonces ese es un caso en el que~
puede no expandirse al valor de$HOME
.bash
antes de bash4 solía realizar globbing tras la expansión de tilde (intenteHOME='/*' bash -c 'echo /*'
). EntoncesHOME=/*; [ "$HOME" = ~ ]
devolvería un error allí.get_current_user_info
, que se usagetpwuid
en todas las plataformas excepto Tandem .