Ecco una soluzione bash solo che ti avrebbe fatto piacere . Questo riduce ogni parte del percorso fino al prefisso più breve che può ancora essere completato da tabulazioni e utilizza * invece di .. come riempitivo.
#!/bin/bash
begin="" # The unshortened beginning of the path.
shortbegin="" # The shortened beginning of the path.
current="" # The section of the path we're currently working on.
end="${2:-$(pwd)}/" # The unmodified rest of the path.
end="${end#/}" # Strip the first/
shortenedpath="$end" # The whole path, to check the length.
maxlength="${1:-0}"
shopt -q nullglob && NGV="-s" || NGV="-u" # Store the value for later.
shopt -s nullglob # Without this, anything that doesn't exist in the filesystem turns into */*/*/...
while [[ "$end" ]] && ((${#shortenedpath} > maxlength))
do
current="${end%%/*}" # everything before the first/
end="${end#*/}" # everything after the first/
shortcur="$current"
shortcurstar="$current" # No star if we don't shorten it.
for ((i=${#current}-2; i>=0; i--))
do
subcurrent="${current:0:i}"
matching=("$begin/$subcurrent"*) # Array of all files that start with $subcurrent.
((${#matching[*]} != 1)) && break # Stop shortening if more than one file matches.
shortcur="$subcurrent"
shortcurstar="$subcurrent*"
done
begin="$begin/$current"
shortbegin="$shortbegin/$shortcurstar"
shortenedpath="$shortbegin/$end"
done
shortenedpath="${shortenedpath%/}" # strip trailing/
shortenedpath="${shortenedpath#/}" # strip leading/
echo "/$shortenedpath" # Make sure it starts with/
shopt "$NGV" nullglob # Reset nullglob in case this is being used as a function.
Assegnare la lunghezza come primo argomento e il percorso come secondo argomento opzionale. Se non viene fornito un secondo argomento, utilizza la directory di lavoro corrente.
Questo cercherà di accorciare in base alla lunghezza indicata. Se ciò non è possibile, dà solo il percorso più breve che può dare.
Algoritmicamente parlando, questo è probabilmente orribile, ma finisce per essere piuttosto veloce. (La chiave per gli script rapidi della shell è evitare sottotitoli e comandi esterni, specialmente nei loop interni.)
In base alla progettazione, si accorcia solo di 2 o più caratteri ('hom *' è uguale a tanti caratteri di 'casa') .
Non è perfetto. Ci sono alcune situazioni in cui non si accorcia il più possibile, come se ci fossero diversi file i cui nomi di file condividono un prefisso (Se esistono foobar1 e foobar2, foobar3 non sarà abbreviato.)
fonte
2009-10-24 05:22:20
Personalmente, ho la prompt solo essere le prime due directory, quindi quanto sopra sarebbe diventato 'li ke/shortened'. Io uso ZSH, però, quindi non so come lo faresti in bash. – pavpanchekha
@pavpanchekha 'pwd | sed -e "s |. */\ (. * /. * \) | \ 1 |" ' – polypus74
E per l'utilizzo in PS1, uno potrebbe: function pwd_depth_limit_2 { if [" $ PWD "=" $ HOME "] then echo -n" ~ " else pwd | sed -e "s |. */\ (. * /. * \) | \ 1 |" fi } – polypus74