for /r 与 for /d 是干什么的
CMD 的 for 循环支持两种目录遍历写法:for /r 从指定根开始递归遍历整棵子树,for /d 只遍历目录名(不深入文件)。相比用 dir /s 再解析文本,for 循环能直接把每个路径交给命令处理,做批量改名、批量复制、按目录统计时更可控。写法上交互式命令行用 %f,批处理里必须写成 %%f。
基本信息
| 适用平台 | Windows CMD(含批处理),XP 起支持 /r |
|---|---|
| 语法 | for /r [根] %f in (模式) do 命令;for /d %d in (通配符) do 命令 |
| 变量写法 | 命令行用 %f,批处理脚本里用 %%f |
| 易踩的点 | 块内计数要开延迟展开(setlocal enabledelayedexpansion) |
典型使用场景
- 批量统计:递归数出某目录下有多少个日志文件与总大小
- 批量处理:对所有 .bak 文件执行删除或改名
- 生成清单:把文件完整路径导成文本交给上级或工单系统
- 按目录操作:只处理一级子目录,比如逐个目录打包
- 定时任务脚本:配合计划任务做每日目录盘点
常用示例
常用示例
:: 交互式:递归列出所有 .log 的完整路径
for /r D:\logs %f in (*.log) do echo %f
:: 只遍历一级子目录名
for /d %d in (D:\www\*) do echo %d
:: 批处理中统计文件数量(需要延迟展开)
setlocal enabledelayedexpansion
set /a n=0
for /r D:\data %%f in (*.dat) do set /a n+=1
echo 共 !n! 个
:: 结果重定向到文件再分析
for /r D:\logs %%f in (*.log) do echo %%f >> D:\list.txt两个开关对比
| 写法 | 遍历范围 | 典型用途 |
|---|---|---|
| for /r | 指定根及其全部子目录中的文件 | 递归查找、批量处理 |
| for /d | 只取目录名,不含文件 | 逐个目录做操作 |
| for %f in (*) | 当前目录一层 | 简单枚举 |
| for /f | 逐行读文件或命令输出 | 解析文本、拆字段 |
路径含空格时命令里要写成 "%f",否则会被拆成多个参数。枚举结果很多时先重定向到文件,再用 findstr 或 PowerShell 分析,比在屏幕上刷过去可靠。
块内的计数与字符串拼接必须用 !n! 而不是 %n%,因为 % 在解析时就被展开。忘记 setlocal enabledelayedexpansion 会得到“计数永远是最后一个值”这类反直觉结果。
for /r 的遍历顺序是“先当前目录再逐层深入”,路径由系统枚举返回。需要按时间或大小排序时,CMD 里做不了,改写 PowerShell 的 Get-ChildItem -Recurse 再 Sort-Object 更合适。
遍历时如果同时在删除或移动被枚举的文件,可能碰到“文件已被占用”或漏处理的情况。稳妥做法是先输出清单(重定向到文件),核对后再另跑一轮做实际动作。