2015-05-11 94 views
3

file1.bat:从另一个批处理文件调用批处理子程序

@echo off 
:Test 
echo in file one 
call file2.bat (Here i want to call only Demo routine in the file2.bat) 

file2.bat:

:hello 
echo in hello 
:Demo 
echo in Demo 

从文件1我想在一个子例程的调用批处理批处理文件2。
我试过例如call file2.bat:Demo但它没有给出正确的结果。

我该如何做到这一点?

回答

3

与子程序的文件必须看起来像:

@echo off 
call :%* 
exit /b %errorlevel% 

:hello 
echo in hello 
exit /b 0 
:Demo 
echo in Demo with argument %1 
exit /b 0 

然后从其他的文件,你可以这样调用它

call file2.bat demo "arg-one" 
+0

您是否阅读过MCND的答案?我认为你喜欢这种技巧或者你已经知道了? – jeb

+0

@jeb - 好戏! – npocmaka

+0

这对我来说看起来更清洁 –

4

你可以写你的函数文件(本示例中是library.cmd) as

@echo off 
    setlocal enableextensions 
    rem Not to be directly called 
    exit /b 9009 

:test 
    echo test [%*] 
    goto :eof 

:test2 
    echo test2 [%*] 
    goto :eof 

:testErrorlevel 
    echo testErrorlevel 
    exit /b 1 

然后调用者批处理可以是类似于

@echo off 
    setlocal enableextensions disabledelayedexpansion 

    call :test arg1 arg2 arg3 
    call :test2 arg4 arg5 arg6 
    call :testErrorlevel && echo no errorlevel || echo errorlevel raised 

    goto :eof 

:test 
:test2 
    echo calling function %0 
    library.cmd %* 

:testErrorlevel 
    echo calling function %0 
    library.cmd 

在这种情况下,标签需要在两个文件中使用相同的名称来定义。

“库”批处理文件的直接调用将替换call :label的上下文,并且在调用批处理时,内部执行goto :label,并且代码在指示的标签内继续。当被调用的批处理文件结束时,上下文被释放并且call :label之后的代码继续。

编辑

如杰布指出在注释中,有在该方法中的缺点。在被调用的批处理文件中运行的代码不能使用%0来检索被调用函数的名称,它将返回批处理文件的名称。但是,如果需要,调用者可以按照示例代码中所示的方式执行此操作。

编辑2016年12月27日

回答到dbenham,我也没有办法知道,如果它是一个编码错误或预期的功能,但是这是如何处理工作

的线条批处理文件在批处理“上下文”创建时在内部BatLoop函数内处理。该函数接收作为其参数之一的指向导致创建“上下文”的命令的指针。

在此函数中,批处理文件中的命令被迭代。循环遍历命令的循环在每次迭代中进行测试:如果启用了扩展,它是批处理文件中的第一行,并且启动上下文的命令的参数以冒号(标号)开头,goto生成跳转到标签。

到此为止,我必须假设这是处理call :label语法的预期行为:创建一个新的“上下文”,加载文件,跳转到标签。

但是接收到的命令参数从不改变,另一个变量用于跟踪批处理文件中命令的执行情况。如果新的批处理文件被加载到/覆盖当前批处理“上下文”(我们还没有使用call命令),加载新的批处理代码后,BatLoop会重置行计数(我们从加载文件的第一行开始)和,voila,循环开始处的条件(扩展启用,第一行,冒号)再次为真(指向的输入命令未更改),并生成新的goto

+1

我喜欢这个技巧,只有一个_drawback_,在辅助批处理的被调用函数中'%0'不包含函数名,它包含批处理文件名,但几乎没有人使用'%0'来检索当前功能名称这是一个非常小的差异 – jeb

+0

惊人的! :-) .... – npocmaka

+0

@jeb,当然你是对的。考虑到有人可能需要函数名称,发布的示例代码包含一个'echo',在将其余工作委托给“库”之前,检索函数名称。现在它被包含在答案中,谢谢。 –

相关问题