Windows Batch 脚本学习

注释

:: 有时候会报错,比如在循环中,遇到这种情况改用REM

REM This is a comment
:: This is a comment too!!(usually!)

关闭、打开回显

ECHO ON 
ECHO OFF
@ECHO OFF

变量

变量不需要声明,没有声明、初始化的变量值为空字符串

SET命令赋值,=号两边不能有空格

DOS是大小写不敏感的,命名temp变量会覆盖系统的TEMP环境变量,注意变量名不要和系统变量冲突

SET foo=bar

/A 参数表示在赋值前先使用数学计算:

SET /A four=2+2
4

% %读取变量:

ECHO %foo%

列出当前变量:

SET

变量默认都是全局的,如果想使用局部变量,先赋值前先使用SETLOCAL,局部变量会在ENDLOCAL之后清除,或是在EXIT命令之后清除,或者是在当前脚本结束时清除:

SETLOCAL 
SET PATH=C:\Windows\system32
ECHO %PATH%

命令行变量使用% 读取,%0为当前运行的批处理文件的命令,%1-%9为第一到第九个参数,常用的变量处理:

  • ~:去除引号
  • d:drive
  • p:path
  • n:file name
  • x:extension
  • f:full name

举例,%~0等于%0去掉双引号,%~n0等于当前批处理文件名,%~dp0等于当前批处理文件父目录

输出使用文件名前缀可以方便定位问题:

ECHO %~n0: some message

脚本常用:

SET me=%~n0
SET parent=%~dp0

返回值

一般,返回0表示执行成功,非0表示失败

环境变量%ERRORLEVEL%包含上一次执行命令或脚本的返回值,可以用来判断是否执行成功

系统自带的命令如ECHOIFSET不会影响这个值

IF %ERRORLEVEL% NEQ 0 (
			REM do something here to address the error
)
SomeFile.exe
IF %ERRORLEVEL% EQU 9009 (
  ECHO error - SomeFile.exe not found in your PATH
)

可以用&&||进行有条件的执行

&&,前面命令运行成功了后面的命令才会执行:

SomeCommand.exe && ECHO SomeCommand.exe succeeded!

||,前面命令运行失败了后面的命令才会执行:

SomeCommand.exe || ECHO SomeCommand.exe failed with return code %ERRORLEVEL%

EXIT命令退出当前批处理脚本,/B参数可以指定ERRORLEVEL,如果没有/B 参数,CMD.EXE会直接退出

SomeCommand.exe || EXIT /B 1

跳转到EOF也可以退出当前批处理脚本并返回1

SomeCommand.exe || GOTO :EOF

可以自定义错误值,方便debug

@ECHO OFF
SETLOCAL ENABLEEXTENSIONS

SET /A errno=0
SET /A ERROR_HELP_SCREEN=1
SET /A ERROR_SOMECOMMAND_NOT_FOUND=2
SET /A ERROR_OTHERCOMMAND_FAILED=4

SomeCommand.exe
IF %ERRORLEVEL% NEQ 0 SET /A errno^|=%ERROR_SOMECOMMAND_NOT_FOUND%

OtherCommand.exe
IF %ERRORLEVEL% NEQ 0 (
    SET /A errno^|=%ERROR_OTHERCOMMAND_FAILED%
)

EXIT /B %errno%

Stdin, Stdout, Stderr

0代表标输入,1代码输出,2代表错误

标准输出重定向,>会覆盖temp.txt,使用>>则是追加temp.txt

DIR > temp.txt
DIR >> temp.txt

使用数字2输出标准错误:

DIR SomeFile.txt  2> temp.txt

同时输出标准输出和标准错误:

DIR SomeFile.txt > output.txt 2>&1

使用文件作为输入:

SORT < SomeFile.txt

抛弃输出,用这个命令可以模拟Linux下的sleep:

PING -n 2 127.0.0.1 > NUL

一个命令的输出作为另一个命令的输入:

DIR /B | SORT

条件语句

检查文件或目录是否存在:

IF EXIST "temp.txt" ECHO found
IF NOT EXIST "temp.txt" ECHO not found

等同于:

IF EXIST "temp.txt" (
    ECHO found
) ELSE (
    ECHO not found
)

检查变量是否存在:

IF "%var%"=="" (SET var=default value)
IF NOT DEFINED var (SET var=default value)

字符串判断:

SET var=Hello, World!

IF "%var%"=="Hello, World!" (
    ECHO found
)

:: 忽略大小写
IF /I "%var%"=="hello, world!" (
    ECHO found
)

数字判断:

SET /A var=1

IF /I "%var%" EQU "1" ECHO equality with 1

IF /I "%var%" NEQ "0" ECHO inequality with 0

IF /I "%var%" GEQ "1" ECHO greater than or equal to 1

IF /I "%var%" LEQ "1" ECHO less than or equal to 1

:: check a return code

IF /I "%ERRORLEVEL%" NEQ "0" (
    ECHO execution failed
)

循环语句

循环变量在CMD命令行窗口中使用单个引号,如%i,在批处理文件中,用两个引号,如%%i

遍历文件:

FOR %II IN (%USERPROFILE%\*) DO @ECHO %I

遍历目录:

FOR /D %I IN (%USERPROFILE%\*) DO @ECHO %I

函数

函数要以:label形式定义在脚本下方,并通过exit /b 语句退出,主程序通过ERRORCODE判断函数运行成功或失败

call :label 调用函数,变量传递和调用脚本一致

%* 表示所有函数参数

@ECHO OFF
SETLOCAL

:: script global variables
SET me=%~n0
SET log=%TEMP%\%me%.txt

:: The "main" logic of the script
IF EXIST "%log%" DELETE /Q %log% >NUL

:: do something cool, then log it
CALL :tee "%me%: Hello, world!"

:: force execution to quit at the end of the "main" logic
EXIT /B %ERRORLEVEL%

:: a function to write to a log file and write to stdout
:tee
ECHO %* >> "%log%"
ECHO %*
EXIT /B 0

Reference

Guide to Windows Batch Scripting

posted @ 2021-08-16 17:35  言谬  阅读(203)  评论(0)    收藏  举报