ZSH ループに引数を追加してコマンドに渡すにはどうすればよいでしょうか?

ZSH ループに引数を追加してコマンドに渡すにはどうすればよいでしょうか?

を使用してmkvmerge、このように配置された複数のMKVクリップにオーディオトラックを追加したい

Clips_folder
/spa/clip1.mka
/spa/clip2.mka
/ger/clip1.mka
/ger/clip2.mka
/clip1.mkv
/clip2.mkv

これが私が持っているスクリプトです(「引数リストに引数を追加」に基づく):

#!/bin/zsh

mkdir -p output

for video in *.mkv
do
    audioargs=("-o ./output/${video} --language 0:eng ${video}")
    for audiodir in *(/)
        do
            audioargs+=("--language 0:${audiodir} ./${audiodir}/${video:r}.mka")
        done
    echo ${audioargs[@]}
done

出力は次のようになります:

-o ./output/clip1.mkv --language 0:eng clip1.mkv --language 0:spa ./spa/clip1.mka --language 0:ger ./ger/clip1.mka

しかし、これを変更してみるmkvmerge ${audioargs[@]}

mkvmerge v45.0.0 ('Heaven in Pennies') 64-bit
Error: no destination file name was given

などに展開されるように正しく渡すaudioargsにはどうすればよいですか?mkvmergemkvmerge -o file --language ...

答え1

テストする必要はありませんmkvmergeが、配列を構築するときに引用符をどのように付けるかが問題だと確信しています。次のようなことをすると

audioargs=("-o ./output/${video} --language 0:eng ${video}")

二重引用符は、全体を 1 つの長い文字列として扱うようにシェルに指示します。そのため、配列内の 1 つの要素として格納され、mkvmerge一連の引数ではなく、スペースを含む単一の引数として渡されます。

echo引数内のスペースと引数外のスペースの区別が隠れていることに注意してください。引数が多すぎるため、このような場合に非常に誤解を招きます。set -xコマンドの前に置くと、実際に何が起こっているかが明確になります。例のファイル名では、set -x何が実行されているかを示します。

echo '-o ./output/clip2.mkv --language 0:eng clip2.mkv' '--language 0:ger ./ger/clip2.mka' '--language 0:spa ./spa/clip2.mka'

長い一重引用符で囲まれたセクションが見えますか? これは、これらが個別の引数のシーケンスではなく、スペースを含む長い引数であることを示しています。

これを解決するには、配列を構築するときに通常の引用符を使用します (つまり、引数をコマンドに直接渡すときに使用するのと同じ引用符)。zsh はデフォルトでは単語を分割しないので、技術的にはまったく引用符を使用する必要はありませんが、私は他のシェルと互換性のある引用符スタイルに従うことを好むため、すべての変数展開を引用符で囲みます。

#!/bin/zsh

mkdir -p output

for video in *.mkv
do
    audioargs=(-o "./output/${video}" --language 0:eng "./${video}")
    for audiodir in *(/)
        do
            audioargs+=(--language "0:${audiodir}" "./${audiodir}/${video:r}.mka")
        done
    echo "${audioargs[@]}"
done

これにより、次の結果が得られますset -x

echo -o ./output/clip2.mkv --language 0:eng ./clip2.mkv --language 0:ger ./ger/clip2.mka --language 0:spa ./spa/clip2.mka

関連情報