【続】call 命令の謎

for /f 版の tail を作るに当たっての難関は、遅延展開を使わないで、添え字付き環境変数へのセットだ。unix で 配列変数機能の無い古い sh では、eval SAVE$J=\$VALUE とやるのが定石だ。これを参考に、左辺は call set SAVE%%J%%= と call を使う方法が思いつく。しかし、単純に、

call set SAVE%%J%%=%%A

とやってしまうと、右辺のfor変数Aに入っている読んだ行に含まれる特殊文字call 時に効いて来るので駄目だ。最初の評価ではfor変数は展開されず、call での再評価時にfor変数が展開されるとうまく行きそうだ。テストのために、

for %%Q in (%%%%) do for /f %%A in ("aaa/?") do call echo %%QA

としてみた。for変数Qの値は %% なので、初回の評価では call echo %%A となり、call による2度目の評価でfor変数Aが展開されると期待した。ところが、表示されたのは、%A である。他にも % の個数を変えたり、^ を使ったりいろいろやってみたがどうもうまく行かない。
どうも、call による再評価は、% 関連処理つまり、
(1) % による環境変数展開 (未定義変数を空にするのも含む)
(2) 連続した %% を % に
(3) 単独の % を削除
を再度行うだけで、for変数や%1等の引数の展開や ^ の処理は call の時点で再度はされないようだ。
call による方法は無理そうだ。

つづく