たとえば、$PWD
/home のサブディレクトリであることを確認します。つまり、文字列が別の文字列で始まるかどうかを確認するために、bash文字列操作を検索しています。
答え1
Bourneスタイルのシェルで文字列が別の文字列のプレフィックスであるかどうかをテストするには、次の手順を実行します。
case $PWD/ in
/home/*) echo "home sweet home";;
*) echo "away from home";;
esac
サフィックスまたはサブストリングテストにも同じ原則が適用されます。case
ファイル名とは異なり、aまたはイニシャルを含む*
すべての文字が設定で一致します。/
.
この構文を実装するシェル[[ … ]]
(bash、ksh、zshなど)では、文字列をパターンと一致させるために使用できます。 (この[
コマンドは文字列の同一性のみをテストできます。)
if [[ $PWD/ = /home/* ]]; then …
現在のディレクトリが下にあるかどうかを具体的にテストする場合、/home
シンボリックリンクがあるため、単純な部分文字列テストでは十分ではありません。
/home
独自のファイルシステムの場合は、現在の.
ディレクトリ()がそのファイルシステムにあるかどうかをテストします。
if [ "$(df -P . | awk 'NR==2 {print $6}')" = "/home" ]; then
echo 'The current directory is on the /home filesystem'
fi
NetBSD、OpenBSD、GNU、busybox、またはtoybox(最後の3つはDebian、OpenWrt、AndroidなどのLinuxベースのシステムで一般的です)がある場合は、パスからシンボリックリンクを削除できますreadlink
。readlink -f
case $(readlink -f .)/ in "$(readlink -f /home)"/*) …
一部のシステムには次のrealpath
コマンドもあります(GNUツールボックスにもあり、現在は推奨されますreadlink
)。
case $(realpath .)/ in "$(realpath /home)"/*) …
シェルには修飾子を持つzsh
独自の演算子もあります。realpath()
:P
if () [[ $1:P/ = $2:P/* ]] . /home; then …
pwd
それ以外の場合は、現在のディレクトリ表示を使用できます。ただし、シェルがcd
コマンドを追跡し、「実際の」場所ではなくディレクトリにアクセスするために使用される名前を保持する場合は、組み込みシェルを使用しないように注意する必要があります。
case $(pwd -P 2>/dev/null || env PWD= pwd)/ in
"$(cd /home && { pwd -P 2>/dev/null || env PWD= pwd; })"/*) …
答え2
ディレクトリが他のディレクトリのサブディレクトリであるかどうかを確実にテストするには、文字列プレフィックスチェック以上が必要です。 Gilesの答えは、このテストを正しく実行する方法を詳しく説明しています。
しかし、単純な文字列プレフィックスチェックを本当にしたい場合(パスを正規化しましたか?)、次の方が良い選択肢です。
test "${PWD##/home/}" != "${PWD}"
"/home/"で始まると、$PWD
左から削除されます。つまり、右側と一致しないため、 "!=" は true を返します。
答え3
おおよそのバージョン:
[ "${PWD:0:6}" = /home/ ]
欠点は、文字数を最初に数える必要があり、/home/
このような一般的なものに置き換えることができないことです$1
。
編集する$VAR
(@Michaelに感謝します)利用可能なものと比較するために一般化
[ "${PWD:0:${#VAR}}" = "$VAR" ]
答え4
質問がよくわかりませんが、両親が自分で見つけなければならないと思います。$PWD、dirname -- "$PWD"
する。親の親を見つけるには、dirname -- "$(dirname -- "$PWD")"
次を実行します。