Y子です。
いろいろバッチファイルを作っていますが、同じような処理をいくつものファイルに書くのは、書くのも読むのもしんどい気がしてきました。
一話完結の記事にするために1つのバッチファイルにまとめ、とは言え再利用しやすくするためにサブルーチン化し、結局は1つのバッチファイルが大きくなる、というジレンマを、最近のわたしは感じていました。
そこで今回は、1ファイルのコード量を減らす目的も兼ねて、処理を複数のバッチファイルに分け、戻り値として値をやり取りする方法を考えます。
概要
バッチファイルから別のバッチファイルを実行し、その実行結果を戻り値として受け取る方法を比較します。
【確認環境:Windows 10 Home (Bld. 19042.928)】
コード
(1) 呼び出される側(errorlevel)
まず、呼び出される側を2種類作ってみます。
引数を与えると、それをそのまま返すという簡単な処理です。
1つ目は、errorlevel
として戻り値を返すタイプ。
本来「終了コード」として使われる環境変数を、バッチファイルの戻り値に流用する手法です。
この手法は、いろいろなサイトで紹介されていました。
exit /b
に続けて値を書いて終了すると、呼び出し側は%errorlevel%
で受け取れます。
@echo off
setlocal
set arg=%~1
exit /b %arg%
endlocal
(2) 呼び出される側(標準出力)
2つ目は、標準出力で戻り値を返すタイプ。
単純にecho
コマンドで値を出力します。
@echo off
setlocal
set arg=%~1
echo %arg%
endlocal
(3) 呼び出す側
前述の(1)(2)に同じ引数を渡し、戻り値を受け取って出力するバッチファイルです。
同じ値に対して、それぞれどのようにふるまうのか、比較できるようにします。
@echo off
setlocal
set arg=%~1
rem 戻り値をerrorlevelで取得
call return_result1.bat %arg%
echo 結果1:%errorlevel%
rem 戻り値をバッチの標準出力から取得
for /f "usebackq" %%a in (`call return_result2.bat %arg%`) do set result=%%a
echo 結果2:%result%
endlocal
実行結果
まずは数字を与えた場合。
どちらの処理も、与えた数字をそのまま取得できるようです。
> call_bat.bat 1
結果1:1
結果2:1
> call_bat.bat 1234567890
結果1:1234567890
結果2:1234567890
次に、文字を与えた場合。
errorlevel
を使う方は、「0」に変わってしまいました。
「終了コード」なので、数字しか戻せないように見えます。
標準出力の方は、問題なく戻り値を取得できました。
> call_bat.bat a
結果1:0
結果2:a
> call_bat.bat abcdefghij
結果1:0
結果2:abcdefghij
ためしに、文字数字交じりも与えてみます。
標準出力の方は、こちらも問題なさそうです。
errorlevel
を使う方は、文字が出てくるとその後が捨てられてしまうようです。
> call_bat.bat 123abc
結果1:123
結果2:123abc
> call_bat.bat abc123
結果1:0
結果2:abc123
> call_bat.bat 1a2b3c
結果1:1
結果2:1a2b3c
おわりに
「戻り値は数字に限る」なんて制約は、無い方がいいですもんね。
errorlevel
は使い勝手が悪いので、echo
の出力を受け取る方法の出番が多そうです。
前回のFIND関数 は、今後ほかのバッチファイルから呼びたい機能です。
見やすさのために「2 文字目」なんて出力にしてしまいましたが、値を他の機能で使うことを考えると、「2」だけにしとけばよかったですね。
では!