[新手上路]批处理新手入门导读[视频教程]批处理基础视频教程[视频教程]VBS基础视频教程[批处理精品]批处理版照片整理器
[批处理精品]纯批处理备份&还原驱动[批处理精品]CMD命令50条不能说的秘密[在线下载]第三方命令行工具[在线帮助]VBScript / JScript 在线参考
返回列表 发帖

[文件操作] 【讨论】这是不是又是for的一个bug

本帖最后由 batman 于 2011-5-28 13:05 编辑

前言:
  这个问题是昨天晚上帮人解决一个文件处理问题时碰到的,害我查错查了一个多小时,最后发现是for /r的问题,现用代码将问题模拟出来,供大家讨论:
  1. @echo off&setlocal enabledelayedexpansion
  2. set "str=temp\"
  3. for /l %%a in (1,1,10) do set "str=!str!%%a\"
  4. if not exist !str! md !str!
  5. for /l %%a in (1,1,100) do cd.>!str!%%a.txt
  6. for /r temp %%a in (*.txt) do (
  7.     echo "%%~dpa"
  8.     for /r "%%~dpa" %%b in (*.txt) do echo "%%b"&pause
  9.   echo ok
  10.     for /r "%cd%\temp\1\2\3\4\5\6\7\8\9\10\" %%b in (*.txt) do echo "%%b"&pause
  11. )
  12. :: 将上面两个&pause去掉就可删除所创建的环境
  13. if exist temp rd /s /q temp
复制代码
  运行这个代码在我本机上的显示如下:

"D:\批处理\test\temp\1\2\3\4\5\6\7\8\9\10\"
ok
"D:\批处理\test\temp\1\2\3\4\5\6\7\8\9\10\1.txt"
请按任意键继续. . .请按任意键继续. . .


  按道理显示应为:

"D:\批处理\test\temp\1\2\3\4\5\6\7\8\9\10\"
"D:\批处理\test\temp\1\2\3\4\5\6\7\8\9\10\1.txt"


  如果for /r "%%~dpa" %%b in (*.txt) do echo "%%~dpb"&pause这句正常运行了,那么程序会在这个pause停住,而下面的ok不会显示出来,但实际上却是在for /r "%cd%\temp\1\2\3\4\5\6\7\8\9\10\" %%b in (*.txt) do echo "%%b"&pause上停住了(ok明显显示出来了),这就说明,第一个for /r没有得到正常运行,那么是不是因为目录级数太多了%%~dpa在for /r 中不能扩展为正确的路径啊?大家不妨展开思考和讨论。。。

ps:就是在回这个贴遇到的问题:http://www.bathome.net/thread-12539-1-1.html,最后将for /r改成for %%b in ("%%~dpa*.txt") do ..才解决问题
***共同提高***

不懂,试了试改成这样也是一样没反应:
  1. for /r %%b in ("%%~dpa*.txt") do echo "%%b"&pause
复制代码

TOP

本帖最后由 batman 于 2011-5-28 12:47 编辑

改成这样就可以了:
  1. for %%b in ("%%~dpa*.txt") do echo "%%b"&pause
复制代码
***共同提高***

TOP

2# zm900612
楼上是不是笔误了,有这样的语法吗?
***共同提高***

TOP

本帖最后由 zm900612 于 2011-5-28 12:56 编辑

4# batman

原来是是语法不对
不是笔误,是我太少用for /r,没什么了解,以为可以这样用

TOP

前言:
for /r "%%~dpa" %%b in (*.txt) do echo "%%b"&pause
[/url]


%%~dpa作为for/r 开关的选项部分参数,在预处理时被读取固定。。。
这和
for /f "delims=%%a" %%b in (".....")do .... 属同一问题:


http://www.bathome.net/viewthrea ... romuid=353#pid80513
1

评分人数

    • batman: 一直忙于测试,没看回贴,呵呵技术 + 1

TOP

运行下面的代码:
  1. @echo off
  2. for %%a in ("%cd%") do (
  3.     echo "%%~dpa"&pause
  4.     for /r "%%~dpa" %%b in (*) do echo "%%b"&pause
  5. )
复制代码
  第一个pause处正确显示%%~dpa对路径的扩展,回车后程序退出,for /r没执行,在cmd中运行也没看到任何报错信息。改成%%~da或%%~pa都是一样的情况,因此,我们可以得出初步结论如下:

  for /r语句中的path是不能用%%~da %%~pa %%~dpa这样的形式来扩展

ps:个人猜测for /r不识别~字符。。。
***共同提高***

TOP

  1. @echo off
  2. for /r "~" %%a in (*) do echo %%a&pause
复制代码
  成功显示信息(实际创建了~目录)
  1. @echo off
  2. for /r "%%~" %%a in (*) do echo %%a&pause
复制代码
  一闪而过(实际创建了%%~目录)

  从此看来不是不识别~字符的问题,真的是预处理的问题,cmd首先将%%~扩展为~变量去寻找其值,而~字符是不能用来做为变量字符的,所以造成了我遇到的问题。唉,真的要把预处理吃透才能避免再出现这样的问题了!
***共同提高***

TOP

%%~dpa作为for/r 开关的选项部分参数,在预处理时被读取固定。。。
这和
for /f "delims=%%a" %%b in (".....")do .... 属同一问题:


http://www.bathome.net/viewthrea ... age=4&fromuid=3 ...
plp626 发表于 2011-5-28 13:14

晕,把这茬忘了

TOP

@echo off
for /r "~" %%a in (*) do echo %%a&pause
  成功显示信息(实际创建了~目录)
@echo off
for /r "%%~" %%a in (*) do echo %%a&pause
  一闪而过(实际创建了%%~目录)

  从此看来不是不识 ...
batman 发表于 2011-5-28 13:53

可为什么我这里可以识别?
  1. @echo off
  2. md %%~
  3. cd.>%%~\test.txt
  4. for /r "%%~" %%a in (*) do echo %%a&pause
复制代码

TOP

for 的 in 前面不能用 %%i !var! 这样的变量,这个以前讨论过的呀。。。
技术问题请到论坛发帖求助!

TOP

哈哈,遇到有挑战性的问题了。

TOP

我懂了,是不是 for /r的 in (set) 中的内容处理发生在迭代之前,就是说(set)中的内容处理时 %%i还是空的。

TOP

13# applba

请打开回显看这段代码:
  1. for %%a in (@) do for /f "tokens=1* delims=%%a" do %%b in ("123@234a345") do echo %%a----%%b
  2. pause
复制代码
我现在才明白“for记住了参数”和“for的参数只参与一次预处理”这两种说法的区别

TOP

楼上多打了个 do
for %%a in (@) do for /f "tokens=1* delims=%%a" do
。。。
解释执行的脚本语言与编译语言还是有很大差别的。。。

TOP

返回列表