Comment pourrais-je obtenir simplement le nom du répertoire de travail actuel dans un script bash, ou mieux encore, juste une commande de terminal.
pwd
donne le chemin complet du répertoire de travail actuel, par exemple, /opt/local/bin
mais je veux seulementbin
Réponses:
Pas besoin de nom de base, et surtout pas besoin d'un sous-shell exécutant pwd (ce qui ajoute une opération fork supplémentaire et coûteuse ); le shell peut le faire en interne en utilisant l' expansion des paramètres :
Notez que si vous appliquez cette technique dans d'autres circonstances (pas
PWD
, mais une autre variable contenant un nom de répertoire), vous devrez peut-être supprimer les barres obliques de fin. Ce qui suit utilise le support extglob de bash pour fonctionner même avec plusieurs barres obliques de fin:Alternativement, sans
extglob
:la source
$PWD
est le nom d'une variable bash intégrée; tous les noms de variables intégrés sont en majuscules (pour les distinguer des variables locales, qui doivent toujours avoir au moins un caractère en minuscule).result=${PWD#*/}
ne pas évaluer à/full/path/to/directory
; au lieu de cela, il supprime uniquement le premier élément, ce qui le rendpath/to/directory
; l'utilisation de deux#
caractères rend le motif correspondant gourmand, en faisant correspondre autant de caractères que possible. Lisez la page d'expansion des paramètres, liée dans la réponse, pour en savoir plus.pwd
n'est pas toujours la même que la valeur de$PWD
, en raison des complications résultant de l'cd
ing via des liens symboliques, si bash a l'-o physical
option définie, et ainsi de suite. Cela était particulièrement désagréable pour la gestion des répertoires montés automatiquement, où l'enregistrement du chemin physique au lieu du chemin logique produirait un chemin qui, s'il était utilisé, permettrait à l'automonteur de démonter spontanément le répertoire utilisé.sh
etcsh
et si vous vouliez que la touche de retour arrière fonctionne, vous deviez lire toute lastty
page de manuel, et nous l'avons aimé!"Utilisez le
basename
programme. Pour votre cas:la source
basename
programme? Quel est le problème avec cette réponse en plus de manquer les citations?basename
est en effet un programme externe qui fait la bonne chose, mais en cours d' exécution tout programme externe pour une bash chose peut faire hors de la boîte en utilisant uniquement la fonctionnalité intégrée est stupide, encourant impact sur les performances (fork()
,execve()
,wait()
, etc.) pour sans raison.basename
ici ne s'appliquent pasdirname
, cardirname
a des fonctionnalités qui${PWD##*/}
ne le font pas - transformer une chaîne sans barre oblique.
, par exemple. Ainsi, bien que l'utilisation endirname
tant qu'outil externe présente un surcoût de performances, il possède également des fonctionnalités qui aident à compenser ces derniers.function
mot-clé est incompatible avec POSIX sans ajouter de valeur à la syntaxe standardisée, et le manque de guillemets créerait des bogues dans les noms de répertoires avec des espaces.wdexec() { "./$(basename "$PWD")"; }
pourrait être une alternative préférable.basename
est moins "efficace". Mais il est probablement plus efficace en termes de productivité des développeurs, car il est facile à retenir par rapport à la syntaxe bash laide. Donc, si vous vous en souvenez, allez-y. Sinon, çabasename
marche aussi bien. Quelqu'un a-t-il déjà dû améliorer les "performances" d'un script bash et le rendre plus efficace?La
la source
echo "${PWD##*/}"
.name=${PWD##*/}
serait bien et cename=$(echo "${PWD##*/}")
serait faux (dans un sens d'inefficacité inutile).Vous pouvez utiliser une combinaison de pwd et de nom de base. Par exemple
la source
Que diriez-vous de grep:
la source
pwd | xargs basename
qu'il ne le fait pas .. probablement pas si important mais l'autre réponse est plus simple et plus cohérente dans tous les environnementsJ'aime la réponse choisie (Charles Duffy), mais faites attention si vous êtes dans un répertoire avec lien symbolique et que vous voulez le nom du répertoire cible. Malheureusement, je ne pense pas que cela puisse être fait dans une expression d'extension de paramètre unique, peut-être que je me trompe. Cela devrait fonctionner:
Pour voir cela, une expérience:
rapports "bar"
DIRNAME
Pour afficher les principaux répertoires d'un chemin (sans encourir un fork-exec de / usr / bin / dirname):
Cela transformera par exemple foo / bar / baz -> foo / bar
la source
readlink -f
c'est une extension GNU, et donc pas disponible sur les BSD (y compris OS X).Si vous utilisez le shell Bourne ou
${PWD##*/}
n'est pas disponible.la source
${PWD##*/}
est POSIX sh - tous les / bin / sh modernes (y compris dash, ash, etc.) le supportent; pour frapper Bourne réel sur une boîte récente, vous devez être sur un système Solaris légèrement ancien. Au-delà de cela -echo "$PWD"
; omettre les guillemets conduit à des bugs (si le nom du répertoire a des espaces, des caractères génériques, etc.).Ce fil est génial! Voici une autre saveur:
la source
Étonnamment, personne n'a mentionné cette alternative qui utilise uniquement les commandes bash intégrées:
En prime, vous pouvez facilement obtenir le nom du répertoire parent avec:
Ceux-ci fonctionneront sur Bash 4.3-alpha ou plus récent.
la source
Utilisation:
OU
Retournez le séparateur de nom de fichier interne (IFS) dans l'espace.
Il y a un espace après l'IFS.
la source
ou
la source
pwd
est divisée en chaînes et étendue par glob avant d'être transmise àbasename
.basename "$(pwd)"
- bien que ce soit très inefficace par rapport à justebasename "$PWD"
, ce qui est lui - même inefficace par rapport à l'utilisation d'une expansion de paramètre au lieu d'appelerbasename
du tout.Pour les jockeys de découverte comme moi:
la source
$PWD
pour"$PWD"
gérer correctement les noms de répertoire inhabituels.je l'utilise habituellement dans les scripts sh
vous pouvez l'utiliser pour automatiser les choses ...
la source
readlink: illegal option -- f usage: readlink [-n] [file ...]
Ci-dessous grep avec regex fonctionne également,
la source
Utilisez simplement:
ou
la source
xargs
formultion est inefficace et bogué lorsque les noms de répertoire contiennent des sauts de ligne littéraux ou des guillemets, et la deuxième formulation appelle lapwd
commande dans un sous-shell, plutôt que de récupérer le même résultat via une expansion de variable intégrée.Si vous souhaitez voir uniquement le répertoire actuel dans la région d'invite bash, vous pouvez modifier le
.bashrc
fichier dans~
. Passez\w
à\W
dans la ligne:Exécutez
source ~/.bashrc
et il affichera uniquement le nom du répertoire dans la région d'invite.Réf: /superuser/60555/show-only-current-directory-name-not-full-path-on-bash-prompt
la source
Vous pouvez utiliser l'utilitaire de nom de base qui supprime tout préfixe se terminant par / et le suffixe (s'il est présent dans la chaîne) de la chaîne, et imprime le résultat sur la sortie standard.
la source
Je préfère fortement utiliser
gbasename
, qui fait partie de coreutils GNU.la source
basename
là. Il n'est généralement appelé quegbasename
sur MacOS et d'autres plates-formes qui autrement sont livrées avec un nom de base non GNU.Les commandes suivantes entraîneront l'impression de votre répertoire de travail actuel dans un script bash.
la source
$1
contiendra le répertoire de travail actuel. (2) Lepushd
etpopd
ne sert à rien ici parce que tout ce qui se trouve à l'intérieur des backticks est fait dans un sous-shell - donc cela ne peut pas affecter le répertoire du shell parent pour commencer. (3) L'utilisation"$(cd "$1"; pwd)"
serait à la fois plus lisible et résistante aux noms de répertoire avec des espaces.