`.bat`、`.cmd`、`.ps1`的区别
下面把 .bat、.cmd、.ps1 三兄弟放在同一张“擂台”上,一眼看清谁是谁、能干什么、不能干什么。
- 出身与运行环境
扩展名 全称/含义 由谁解释执行 必需环境
.bat Batch file cmd.exe(16/32/64 位 NT 系列命令解释器) 任何 Windows 都自带
.cmd Command file cmd.exe(与 .bat 同一个进程) 任何 Windows 都自带
.ps1 PowerShell Script powershell.exe / pwsh.exe(PowerShell 宿主) 需要安装 PowerShell(Win10/11 已内置;Win7 需手动装)
- 语法能力速览
特性 .bat / .cmd .ps1
变量 纯文本 %var% 强类型 $var
流程控制 if errorlevel、for /f、goto if、foreach、while、switch、异常处理 try/catch/finally
函数 靠 call :label 模拟,无返回值 真正函数 function foo($arg){...},可返回任意对象
错误处理 只能靠 errorlevel 整数 结构化异常, $? $Error $LASTEXITCODE
管道 纯文本流 对象管道(传递 .NET 对象,无需解析文本)
调用外部命令 直接可执行 同样可执行,还可调用 .NET 方法、COM、WMI、REST API
跨平台 ❌(仅 Windows) ✅(PowerShell Core / 7+ 支持 Win/Linux/macOS)
- .bat 与 .cmd 的微观差异(99% 场景可忽略)
- 在 NT 系列内核(Windows 2000 以后)里,
.bat与.cmd都由cmd.exe解释; - 唯一残留差异:
.bat文件在 COMMAND16(DOS)时代会被command.com执行;.cmd文件只在cmd.exe里运行;
- 因此老书籍会说 “
.cmd稍微快一丢丢、少一次 16 位回退检测”,但现代 64 位 Windows 已根本不再加载command.com,两者实际行为完全一致。
→ 结论:今天写新脚本,选 .bat 或 .cmd 纯粹看个人口味;微软官方示例多用 .cmd。
- 执行策略差异(最容易踩坑)
扩展名 双击能否直接跑 默认是否被阻止 如何改策略
.bat / .cmd ✅ 不阻止 无需额外设置
.ps1 ❌(默认用记事本打开) 被阻止 需 Set-ExecutionPolicy RemoteSigned -Scope CurrentUser 等
- 场景一句话总结
- 快速、简单、只调系统命令 → 写
.bat/.cmd即可; - 要函数、要对象、要远程管理、要跨平台 → 上
.ps1; - 老脚本维护 → 看到
.bat别惊讶,继续用; - 写新脚本但只跑 Windows → 推荐
.ps1,微软已经把未来押在 PowerShell 上。
- 速查表(打印贴墙)
.bat ≈ .cmd (cmd.exe,纯文本,老平台通用)
.ps1 (powershell,对象化,现代化,跨平台)
