批处理脚本学习笔记
原创作品,允许转载,转载时请务必以超链接形式标明文章原始出处、作者信息和本声明。否则将追究法律责任。http://blog.csdn.net/taotaoyouarebaby/article/details/23958897
说明:本文档在LGPL开源协议下发布。本文档将批处理当作一门编程语言来看待,按编程语言的元素来组织内容。这份文档是目的不是教你各个命令的语法,而主要集中在批处理是怎样实现普通编程语言的一些功能,其中的语法说明使用的是BNF规则。文档有一定难度,不适合于连批处理是什么都不知道的情况。如果你有点编程语言基础那就更好了。完完整整的把批处理看下来,得到一个结论就是,批处理功能非常有限,很难当作一门完整的编程语言来看待!复制到网页上之后格式有点乱,所以提供PDF下载。
1 cmd解释器基本工作原理
所有命令不区分大小写,除for的循环变量。
cmd解释器按逻辑行读取和执行。行在这是的含义:1.以回车为结束标志的一自然行。2.通过()和&&,||,&组合在一起的多个自然行。
读取一行之后,会执行以下步骤:
1) 变量替换:将参数变量(%0, %1,...,%9)和以%号引起来变量(eg: %path%)替换为实际值。
2) 去除被转义的特殊字符的语义。转义字符:""(对之间的所有元字符转义), ^(对单个字符转义)
3) 执行语法检查,生成指令序列。
4) 执行重定向
1.1 延迟绑定技术
语法:
setlocal EnableDelayedExpansion | DisableDelayedExpansion set var=!var!;... ... endlocal |
功能:
1) 使用变量在逻辑行执行过程中的实际值(动态变化),而不是读取逻辑行时的值(不变,只是简单替换)。主要用于for语句。如果不启动的话,for语句中使用set命令时,多数情况下无法得到想要的结果。
2) 需要延迟绑定的变量,通过!var!的形式来获取值。支持同样的字符串操作。
1.2 命令扩展
语法:
setlocal EnableExtensions | DiableExtensions ... endlocal |
功能:打开一些命令的扩展功能。
2 批处理基本语法
注释:
rem anything :: anything. 解释器无法识别::所以会抛弃这一行,达到注释的效果。由此可以得到其它的注释方式。 |
2.1 变量
2.1.1 简单变量
定义:
set variable-name=value{ value} value := %var% | %1 | string | numbers |
说明:
1) 变量名与变量值之间不能有空格
2) 变量值不能有特殊字符,如果有则需要转义。
3) 变量可以重复定义。重定义时会覆盖之前定义的值。
4) 从用户输入或文件取得变量值
set /p var=提示语句 set /p var= < file.txt |
删除:
set variable-name= |
显示:会显示所有以variable-name为前缀的变量的值
set variable-name |
引用:
%变量名% |
使用示例:
@echo off set var=value echo %var% pause |
输出:value
|
2.2 输入输出
2.2.1 输出
控制输出 |
描述 |
示例 |
echo |
输出一行信息 |
echo %var% 输出变量值 echo %1 输出命令行参数值 echo some-message. 输出任意信息 echo >>file.txt str 等同于:echo str >>file.txt |
type |
打印文本信息到标准输出 |
type a.txt 显示a.txt中的内容 |
more |
逐屏显示 |
type a.txt | more +3
|
CLS |
清屏 |
路过前3行,逐屏显示a.txt内容 |
COLOR |
设置cmd文字与背景颜色 |
color 07 背景(0:黑色)文字(7:白色) |
TITLE |
设置cmd标题,常当作进度条用 |
@title welcome to GOD 进度条程序 |
@ |
隐藏命令 |
@echo 不显示命令 |
time /t |
显示当前时间 |
|
2.2.2 标准输出输出句柄
句柄 |
等价的数字 |
描述 |
STDIN |
0 |
标准输入,即键盘输入 |
STDOUT |
1 |
标准输出 |
STDERR |
2 |
标准错误输出 |
UNDEFINED |
3-9 |
应用程序定义 |
2.2.3 输入输出重定向与管道命令
命令 |
描述 |
> |
将标准输出重定向到文件,即将输出写入文件。以覆盖方式写入。 |
>> |
将标准输出重定向到文件,即将输出写入文件。以在尾部追加的方式写入。 |
< |
将标准输入重定向到文件,即从文件中读取输入数据。 |
| |
a | b,将a命令的输出作为b命令的输入。名叫管道。 |
<& |
管道合并命令。a<&b 等价于 b>&a。将要输出到b的内容,输出到a。将b管的出口合并到a管的入口。 常用形式:type a.txt > b.txt 2 >& 1,将type的错误信息输出到标准输出。并将标准输出重定向到文件。 |
>& |
常见:
1) command > nul 等价于command 1>nul : 不显示command命令的输出信息。
eg: copy a.txt b.txt >nul.这样一来就不会显示复制完成的提示信息了。
2) command 2>nul : 不显示command命令的标准错误信息。
2.3 字符串
2.3.1 常用字符串操作
操作 |
描述 |
||||||||
定义/创建 |
set str=a;b;c;d |
||||||||
连接 |
set str=%str%otherthings |
||||||||
替换 |
set str=%str:a=c% 把str中的所有a替换为c set str=%str:*;=% 把str中从开始到’;’为止(包含’;’)的所有内容替换为空(即删除) |
||||||||
剪切 |
%str:~start[,end]% 1) 字符串下标从0开始。得到的字符串,如果start==0, 为(str[start],str[end-1]);start!=0, 为(str[start], str[end])。 2) start,end的取值区间:(-len, -1] & [0, len-1),负数表示从后往前数的位置。
|
||||||||
清空 |
set str= |
2.3.2 处理字符串中的保留字符
windowsNT的保留字符:& | ( ) < > ^。当字符串有以上字符只需要使用字符’^’对其进行转义。
一般情况:
set var=dir ^> file.txt & rem 转义单个保留字符 set var=”dir > file.txt” & rem 会转义双引号中的所有保留字符,但var中会含有双引号 |
嵌套时:
@IF NOT "%~1"=="" FOR /F "tokens=2*" %%A IN ( 'REG Query HKLM\SOFTWARE\PHP /v InstallDir' ) DO ( @FOR /F %%C IN ( '%%~sB.\PHP.EXE -r "print^(md5^(\"%~1\"^)^)^;"' ) DO @SET MD5=%%C ) |
说明:each level of nesting would require an extra "level" ofescaping
2.3.3 示例
显示一个变量中所有以分号分隔的字符串。
@echo off set myvar=a b;c;d set strippedvar=%myvar% :repeat for /f "delims=;" %%a in ("%strippedvar%") do echo %%a set prestrippedvar=%strippedvar% set strippedvar=%strippedvar:*;=% if not "%prestrippedvar:;=%"=="%prestrippedvar%" goto :repeat |
2.4 算术运算SET /A
支持的数
Octal: |
SET /A Result = 020 |
Decimal: |
SET /A Result = 16 |
Hexadecimal: |
SET /A Result = 0x10 |
Or any combination: |
SET /A Result = 010 + 0x20 - 24 |
算术运算汇总:对所有操作符支持复合赋值(eg: +=, -=)
Add: |
SET /A Result = 12 + 4 |
Subtract: |
SET /A Result = 23 - 7 |
Multiply: |
SET /A Result = 8 * 2 |
Integer divide: |
SET /A Result = 33 / 2 |
SET /A "Result = 66 %% 25" |
|
Shift right: (2) |
SET /A "Result = 128 >> 3" |
Shift left: |
SET /A "Result = 1 << 4" |
Bitwise AND: |
SET /A "Result = 48 & 23" |
Bitwise OR: |
SET /A "Result = 16 | 16" |
Bitwise XOR: |
SET /A "Result = 31 ^ 15" |
Group: |
SET /A "Result = ( 24 << 1 ) & 23" |
说明:
1.取模运算,在批处理中使用%%,在命令行中使用%。
2.当表达式包含特殊字符(%
, &
, <
, >
, |
, ˆ
, (
or )
)时,需要使用双引号引起来。
3.不支持实数(小数)运算
2.5 DOSKEY与命令别名
语法:
doskey macroname=[comand{$Tcommand}] 设置命令别名,等号右边不能以空格开头。 doskey /MACROFILE=filename 从文件中导入命令别名设置 doskey /MACROS:ALL > filename 将所有命令别名设置导出到文件 |
Doskey宏定义的一些特殊代码:
特殊代码 |
含义 |
示例 |
$T |
命令分隔符。允许一个宏中存在多个命令。 |
doskey ls=dir$Techo end |
$1-$9 |
接收对应的批处理参数。与批处理程序中的 %1-%9 等同。 |
|
$* |
接收别名后面的所有参数 |
doskey ls=dir $* |