for /f "tokens=*" %%a in ('find /v ":" "%appdata%\gamelauncher\options.txt" ^| find "menu=a"') do ( set usemenu=a )
for /f "tokens=*" %%a in ('find /v ":" "%appdata%\gamelauncher\options.txt" ^| find "menu=b"') do ( set usemenu=b )
for /f "tokens=*" %%a in ('find /v ":" "%appdata%\gamelauncher\options.txt" ^| find "menu=c"') do ( set usemenu=c )
右、このコード(機能しない可能性があること、私が見つけようとしていること)では、この「%」aが「for」コマンドに含まれています。
まず、%variable%と%% aの違いは何ですか?
次に、誰かが「for」コマンドを私に説明できますか?私はグーグルでやりすぎたし、すべての説明は複雑に思える...
私がしようとしているのは、options.txtから変数をプルすることです。これにより、ゲームランチャーのメニュースタイルを変更できます。 3つのスタイル(a、b、c)があるので、options.txtが「menu = a」を読んだ場合、%usemenu%などの変数をaの値に設定するにはどうすればよいですか?
事前に助けをありがとう!
_%variable%
_は環境変数です。これらはset
で設定され、_%foo%
_または_!foo!
_でアクセスできます(有効になっている場合は拡張の遅延あり)。 _%%a
_は、現在のループ項目または現在の行のトークンを表すためにfor
コマンドによって作成された特別な変数です。
for
はおそらく、バッチファイルの最も複雑で強力な部分です。ループが必要な場合は、ほとんどの場合for
で対応できます。 _help for
_には概要があります。
あなたはできる
for %x in (*.txt) do ...
for /l %x in (1, 1, 15) do...
(引数はstart、stepおよびend)for %x in (a, b, c) do ...
for /f %x in (foo.txt) do ...
for /f "tokens=2,3* delims=," %x in (foo.txt) do ...
for /f %x in ('somecommand.exe') do ...
これは短い概要です。より複雑になりますが、そのためのヘルプを読んでください。
_%%a
_(またはfor
がバッチファイルの外部で使用されている場合は_%a
_)の形式の変数は、バッチファイルおよびサブルーチン(_%1
_、_%2
_、...)。たとえば、変数が_%%~nxa
_を使用してパスを持つファイル名を表す場合に、ファイル名と拡張子のみを取得するなど、いくつかの種類の拡張をそれらに適用できます。それらの完全な概要は_help for
_にあります。
一方、環境変数には他の種類の特別なものがあります。 a
がb
で置き換えられることを除いて、_%foo:a=b%
_を介してそれらの置換を実行できます。結果は_%foo%
_になります。また、部分文字列を取ることもできます:_%foo:~4,2%
_。それらの説明は_help set
_にあります。
なぜ_%variables%
_と_%%a
_が異なるのかについては、答えるのが少し難しく、おそらく歴史的な奇妙さだけでしょう。上で概説したように、for
で使用されている変数と非常によく似た第3の種類の変数_%1
_などがあり、より長く存在していると思います。環境変数はブロックのためにfor
で使用するのが少し扱いにくく、遅延拡張に大きく依存しているため、環境変数の代わりに引数と同じメカニズムを使用する決定が行われた可能性があります。
また、プロセスが_variable=value␀
_ペアに格納されるメモリの特別な「環境」ブロックを持っていることを考えると、環境変数はより高価になる可能性があるため、環境変数の更新には、他の種類のメモリ変数はより軽量になる可能性があります。しかし、これは推測です。
あなたの問題に関して、あなたは本当にここにfor
を必要としません:
_find /v ":" "%appdata%\gamelauncher\options.txt" | find "menu=a" && set usemenu=a
_
これは、前のコマンドが成功した場合、つまり_menu=a
_が見つかった場合にのみset
を実行します。これはfor
よりもはるかに簡単です。私が読んだものから、コロンを含まない行に_menu=a
_が存在するかどうかを確認しようとしていますが、その場合、usemenu
をa
に設定する必要がありますよね? (そしてb
とc
の場合も同様です。ファイルまたは出力の行をループして適切にトークン化することにより、for
をそれを実行するように調整することができます。 menu
ですが、行の形式によっては、これはトリッキーになる場合があります。理論的に機能している場合は、それをそのまま使用する必要があります。ただし、ループを使用して同じことを繰り返さないようにすることができます。 a
、b
、c
の3回の行:
_for %%X in (a b c) do (
find /v ":" "%appdata%\gamelauncher\options.txt" | find "menu=%%X" && set usemenu=%%X
)
_
ただし、解析しているファイルが単純な場合は、各行に_name=value
_のペアだけがあり、_: foo
_がコメントになる場合、could use for
同様に:
_for /f "tokens=1,* eol=: delims==" %%A in (%appdata%\gamelauncher\options.txt) do (
if "%%A"=="menu" set usemenu=%%B
)
_
しかし、それはファイルの正確なフォーマットに少し依存します。上記のスニペットは、ファイルを1行ずつ読み取り、各行でコロンの後のすべてを破棄します(_eol=:
_オプション)。等号をトークンの区切り文字として使用し、2つのトークンをキャプチャします:最初の_=
_およびその後のすべて。トークンは_%%A
_で始まる名前が付けられているため、2番目のトークンは暗黙的に_%%B
_です(これも_help for
_で説明されています)。次に、各行で最初のトークンを調べて、それがmenu
であるかどうかを確認し、そうである場合は、その値をusemenu
変数に割り当てます。あなたがこれをサポートする多くの可能なオプションを持っているなら、これは確かに維持するのがより簡単です:-)。