1
  • その中に4つのディレクトリがあるディレクトリがあります。
  • 5番目のディレクトリ(cx1_date)を作成し、元のディレクトリと同じ名前の空のディレクトリを4つ作成したい
  • 次に、元の各ディレクトリから 2 つのファイルをそれぞれの名前で新しいサブディレクトリにコピーします。
  • PWD自体をコピーしようとするため(これはfind呼び出しの結果として表示されるため)、エラーが発生していると思うので、ifステートメントを含めようとしましたが、機能しないと思います

    now=$(date +"%m_%d_%Y")
    
    PWD="/nmr/charlie"
    
    mkdir $PWD/cx1_$now
    
    for name in $(find $PWD -maxdepth 1 -type d); do
    if [[ "$name" = "$PWD" && "$PWD" = "$name" ]];
    then 
        :
    else 
        cd $PWD/cx1_$now
        mkdir $PWD/$name
        cd $PWD/$name 
        cp file1.ext $PWD/cx1_$now/$name
        cp file2.ext $PWD/cx1_$now/$name
    fi 
    done
    

エラーの最初の行

mkdir: ディレクトリ `/nmr/charlie/cx1_05_15_2012//nmr/charlie/cx1_05_15_2012' を作成できません: そのようなファイルまたはディレクトリはありません

どうぞよろしくお願いいたします。

チャーリー

4

2 に答える 2

2

2番目mkdirは必要ありません$PWD

now=$(date +"%m_%d_%Y")

DIR="/nmr/charlie"

mkdir $DIR/cx1_$now

for name in $(find $DIR -maxdepth 1 -type d)
do
    if [[ "$name" != "$DIR" ]]
    then 
        (cd $DIR/cx1_$now; mkdir $name)
        (cd $DIR/$name 
         cp file1.ext $DIR/cx1_$now/$name
         cp file2.ext $DIR/cx1_$now/$name
        )
    fi
done

また、PWD は組み込み変数です。cd設定しないでください (コマンドを使用する場合を除く)。

の対称テストは必要ありませんif。空の句を避けるため!=に代わりに使用できます(OK、いい anodyneコマンドが含まれています。テストを反転する場合は必要ありません)。=then:

私は通常、cd操作をサブシェルに入れます。そうすれば、私は混乱することが少なくなります。2 行目の代替案は次のとおりです。これは、またはサブシェルmkdirを必要としません。cd

mkdir -p $DIR/cx1_$now/$name

日付には、次のような ISO 8601 形式を使用することをお勧めします。

now=$(date +"%Y_%m_%d")

そうすれば、ディレクトリは日付順に自動的にソートされます。


私はまだエラーが発生します:

mkdir: cannot create directory `/nmr/charlie/directory_name_1': File exists
/home/charlie/Desktop/scripts/test.sh: line 16: cd: /nmr/charlie//nmr/charlie/directory_name_1: No such file or directory 

この問題は、まだ正しくフィルタリングされていないことを意味している可能性があります。たとえば、バックアップ ディレクトリを作成するたびに、以前のすべてのバックアップ ディレクトリが新しいディレクトリにバックアップされますが、これは少し過剰です。したがって、演習の他の部分は、findbetter の出力をフィルタリングすることです。

...そして、ディレクトリのベース名を使用する必要があり、すべてのcd操作も回避できます。

now=$(date +"%m_%d_%Y")

DIR="/nmr/charlie"

mkdir $DIR/cx1_$now

for name in $(find $DIR -maxdepth 1 -type d | grep -v '/cx1_[^/]*$')
do
    if [[ "$name" != "$DIR" ]]
    then
        targetdir=$DIR/cx1_$now/$(basename $name)
        mkdir -p $targetdir
        cp $name/file1.ext $name/file2.ext $targetdir
    fi
done

「sh -x script.sh」または「bash -x script.sh」を使用してスクリプトを実行し、それが何をしているかを確認することについて知っていますか。リストからバックアップディレクトリのように見えるものをすべて除外するif条件が必要かどうかさえわかりません。grep

これは、ディレクトリ パスが正常で、スペースが含まれていない場合にのみ機能することに注意してください。移植性のないファイル名 (移植性のある名前[-_.A-Za-z0-9]のみが使用される場合) を使用すると、事態は急速に悪化します。改行とスペースは本当に混乱します。

/nmr/backup/charlieディレクトリの下またはそれ以外の場所にバックアップを作成した場合、これはより簡単になることに注意してください/nmr/charlie。ただし、注意すれば、要求に応じてその場で行うことができます。

于 2012-05-15T15:43:57.567 に答える
2

「/nmr/charlie」と「/nmr/charlie/cx1_date」の両方を意味するかのように $PWD を使用しています。それは最初のものだけを意味します。

また、$PWD 内のフォルダーをループすると、cx1_date も含まれます。これは既に作成済みであるため、確認する必要があります。

PWD は他の用途にも使用できるため、変数名として使用することはお勧めしません。

[編集] また、 $name はディレクトリのフル パスを取得するため、basename を使用して、フル パスなしでディレクトリの名前のみを取得する必要があります。また、if 行を間違えて、2 番目の比較で = ではなく != にするつもりでした。申し訳ありませんが、テストする時点でシェルがありませんでした。以下のコードが動作するようになりました。テスト済みです。

これはうまくいくはずです:

now=$(date +"%m_%d_%Y")

DIR="/nmr/charlie"

mkdir $DIR/cx1_$now

for name in $(find $DIR -maxdepth 1 -type d)
do
    if [[ "$name" != "$DIR" && "$name" != "$DIR/cx1_$now" ]];
    then 
        targetdir=$(basename $name)
        cd $DIR/cx1_$now
        mkdir $DIR/cx1_$now/$targetdir
        cd $DIR/$targetdir
        cp file1.ext $DIR/cx1_$now/$targetdir
        cp file2.ext $DIR/cx1_$now/$targetdir
    fi 
done
于 2012-05-15T15:47:10.467 に答える