La variable $ 0 contient les informations de chemin du script.
- Comment puis-je changer les informations de chemin en chemin absolu? Je veux dire comment traiter ~,., .. ou similaire?
- Comment puis-je diviser les informations de chemin en répertoire et nom de fichier?
Je pourrais utiliser python / perl pour cela, mais je veux utiliser bash si possible.
Réponses:
Vous n'avez pas besoin de traiter des choses comme
~
, le shell le fait pour vous. C'est pourquoi vous pouvez passer~/filename
à n'importe quel script ou programme et cela fonctionne - tous ces programmes ne se gèrent pas~
eux-mêmes, votre shell convertit l'argument/home/username/filename
et le transmet au programme à la place:Si vous avez besoin d'un nom de fichier canonique (qui n'inclut pas de choses comme
..
), utilisezrealpath
(merci Neil ):Pour diviser le chemin en nom de répertoire et nom de fichier, utilisez
dirname
etbasename
:la source
realpath
est mieux, maisreadlink
semble fonctionner quand je l'essaye; connaissez-vous un exemple où il échoue?cd /tmp; touch foo; ln -s foo bar; cd; readlink /tmp/bar
. Cela revientfoo
etrealpath
revient/tmp/foo
, ce que vous voulez.readlink -f
(note-f
) est presque équivalent àrealpath
, et il est plus portable:readlink -f
dans GNU coreutils et existe également sur quelques autres systèmes;realpath
est empaqueté séparément et ne peut pas être installé (par exemple, seuls 5 paquets non communs en dépendent dans Ubuntu 10.04 ou Debian Lenny).Utiliser dirname et basename comme mentionné par Michael devrait être le moyen le plus sûr d'obtenir ce que vous voulez.
Quoi qu'il en soit, si vous voulez vraiment le faire avec des "outils bash uniquement", vous pouvez utiliser la substitution de paramètres:
Cet exemple est directement tiré du Guide de script Bash avancé qui vaut le détour.
L'explication est assez simple:
Regardez le modèle comme une expression régulière et le
#
ou##
comme une sorte de modificateur gourmand / non gourmand.Cela peut devenir utile si vous devez effectuer des extractions plus compliquées d'une partie de chemins.
la source
${...##...}
et des amis plutôt quedirname
etbasename
qu'ils ne fonctionnent pas dans tous les cas. Par exemple, les deux${0##*/}
et${0%/*}
développez la même chose que$0
si$0
ne contient pas de/
.${0%/*}
n'est pas une bonne alternative àdirname
. Cependant, quel est le problème avec l'utilisation${0##*/}
au lieu debasename
?$0
est un nom de répertoire avec une fin/
. Mais je regrette mes conseils, cardirname
ne fait pas mieux.realpath
est une commande qui vous indique le vrai chemin (supprime .. et les liens symboliques etc.)Il est standard avec FreeBSD. Selon cette discussion, il est également disponible pour Linux:
http://www.unix.com/shell-programming-scripting/89294-geting-real-path.html
Cette discussion offre également une solution bash:
la source