如何使用批处理文件遍历目录结构



我正在编写一个Windows批处理脚本,该脚本编译作为参数传递给它的文件。以下是我想做的:

  1. 转到每个文件位置
  2. 在当前文件夹中搜索"makefile"
  3. 如果找到,运行"make"并中断,否则转到父文件夹并重复步骤2
  4. 如果到达当前驱动器的根目录,则退出

以下是我到目前为止所能想到的:

输入:要编译的文件的完整路径列表。

示例:";D:/dir1/dir2/file1.cxx"D:/dir1/dir3/file2.cxx";

@echo off
REM -- loop over each argument --
for %%I IN (%*) DO (
   cd %%~dpI
   call :loop
   echo "After subroutine"
)
exit /b

:loop
REM -- NOTE: Infinite loop, breaks out when root directory is reached --
REM -- or makefile is found                                           --
for /L %%n in (1,0,10) do (
   if exist "makefile" (
      echo "Building.."
      make -s
      echo "Exiting inner loop"
      exit /b 2
   ) else (
      if "%cd:~3,1%"=="" ( 
        echo "Reached root...exiting inner loop..."
        exit /b 2
      )
      REM -- Go to parent directory --
      cd ..
      echo "Searching one level up"
   )
)

除此之外,所有文件都正常工作-遇到第一个"makefile"后,"退出/b 2"会导致批处理文件退出。我想要的是,只有内部循环应该退出退出/b 2"应该根据此操作,但由于某些原因,它不是。有人能帮我吗?

您的代码中有几个问题。不太重要的一点是,必须使用延迟扩展来比较内部循环中的当前目录。现在重要的一个:

使用exit /B命令无法中断for /L循环。尽管循环中exit /B之后的任何命令都不再执行,但循环永远不会结束。您必须使用普通的exit命令来执行此操作,但当然整个cmd.exe会话也会被exit终止,因此解决方案是启动第二个cmd.exe会话,该会话将重新执行由特殊参数控制的同一批处理文件

@echo off
REM If this batch file was re-executed from itself: goto right part
if "%~1" equ ":loop" goto loop
REM -- loop over each argument --
for %%I IN (%*) DO (
   cd %%~dpI
   REM Execute the "subroutine" in a separate cmd.exe session
   cmd /C "%~F0" :loop
   echo "After subroutine"
)
exit /b

:loop
setlocal EnableDelayedExpansion
REM -- NOTE: Infinite loop, breaks out when root directory is reached --
REM -- or makefile is found                                           --
for /L %%n in () do (
   if exist "makefile" (
      echo "Building.."
      make -s
      echo "Exiting inner loop"
      exit
   ) else (
      if "!cd:~3,1!" equ "" ( 
        echo "Reached root...exiting inner loop..."
        exit
      )
      REM -- Go to parent directory --
      cd ..
      echo "Searching one level up"
   )
)

编辑添加了几条评论

  • 当您使用无限循环时,括号中不包含任何值会更清楚;否则,您似乎在"0"增量中犯了一个错误。

  • 出现在您给出的链接上的EXIT命令的描述在这一点上是不正确的。。。

最新更新