Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/batch-file/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
避免在Windows批处理文件中同时调用_Windows_Batch File_Semaphore - Fatal编程技术网

避免在Windows批处理文件中同时调用

避免在Windows批处理文件中同时调用,windows,batch-file,semaphore,Windows,Batch File,Semaphore,我有一个通用的windows构建批处理(即build.bat),它以不同的参数在Parralel中运行 start build.bat device1 start build.bat device2 start build.bat device3 但在该批处理中,有一个可执行文件在Parralel中被调用时崩溃 使用windows内置函数,是否可以在调用已在另一批中运行时阻止该调用,并在该批中完成后继续 假设该批次的内容是 start delay 5 当批处理多次被调用时,当另一个延迟正在运

我有一个通用的windows构建批处理(即build.bat),它以不同的参数在Parralel中运行

start build.bat device1
start build.bat device2
start build.bat device3
但在该批处理中,有一个可执行文件在Parralel中被调用时崩溃

使用windows内置函数,是否可以在调用已在另一批中运行时阻止该调用,并在该批中完成后继续

假设该批次的内容是

start delay 5
当批处理多次被调用时,当另一个延迟正在运行时,该延迟不能运行

这与信号量类似

所以我们的目标是拥有这样的东西

CheckAndWaitIfDelayIsRunning
start delay 5

提前感谢。

您可以使用
文件锁定来批量构建信号量

:lock
2>nul (
  > sema1.lock (
    delay 5
    REM The next line is for proper finishing the lock block
    (call )
  )
) || goto :lock
诀窍在于,一次只允许一个进程写入sema1.lock。
任何其他进程都将失败并跳过内部块,
| | goto:lock
将重试,直到可以写入sema1.lock文件。
这种技术的一个缺点是占用CPU,因为这个信号量不是真正的等待,它更像是一个轮询信号量


有关更多信息,请参见

您可以通过使用文件锁定来批量构建信号量

:lock
2>nul (
  > sema1.lock (
    delay 5
    REM The next line is for proper finishing the lock block
    (call )
  )
) || goto :lock
诀窍在于,一次只允许一个进程写入sema1.lock。
任何其他进程都将失败并跳过内部块,
| | goto:lock
将重试,直到可以写入sema1.lock文件。
这种技术的一个缺点是占用CPU,因为这个信号量不是真正的等待,它更像是一个轮询信号量


更多信息请参见

根据答案,我优化了两件事:

  • 控制台输出仍然可见,并且没有重定向到文件中
  • %errorlevel%包含来自我的任务的错误
它将文件夹用作第一次创建的锁。
Ping用作等待时间并设置为1000毫秒。
它统计线程在获得执行其任务的权限之前等待的周期数

脚本

set lockMyName="%TEMP%\my.lock"    
set lockMyCounterMs=0
set lockMyTimeMs=1000
@echo  [ INFO ] Getting my lock...
:lock_my
md %lockMyName% 2>nul
if "%errorlevel%" neq "0" (
    set /a lockMyCounterMs+=%lockMyTimeMs%
    :: commonly used timeout without waiting for input (must be invalid ip address)
    ping 1.0.0.0 -n 1 -w %lockMyTimeMs% >nul
    goto :lock_my
)
@echo  [ INFO ] ... locked ^(waited %lockMyCounterMs% ms for lock^)

 ::do your task here

@echo  [ INFO ] ...release my lock
rd /Q %lockMyName% 2>nul

根据答案,我优化了两件事:

  • 控制台输出仍然可见,并且没有重定向到文件中
  • %errorlevel%包含来自我的任务的错误
它将文件夹用作第一次创建的锁。
Ping用作等待时间并设置为1000毫秒。
它统计线程在获得执行其任务的权限之前等待的周期数

脚本

set lockMyName="%TEMP%\my.lock"    
set lockMyCounterMs=0
set lockMyTimeMs=1000
@echo  [ INFO ] Getting my lock...
:lock_my
md %lockMyName% 2>nul
if "%errorlevel%" neq "0" (
    set /a lockMyCounterMs+=%lockMyTimeMs%
    :: commonly used timeout without waiting for input (must be invalid ip address)
    ping 1.0.0.0 -n 1 -w %lockMyTimeMs% >nul
    goto :lock_my
)
@echo  [ INFO ] ... locked ^(waited %lockMyCounterMs% ms for lock^)

 ::do your task here

@echo  [ INFO ] ...release my lock
rd /Q %lockMyName% 2>nul

插入
timeout 1
命令以降低轮询率如何?这行得通吗?是的,这行得通,但会减慢程序的反应,因为semaLock在等待另一个线程的释放时平均会等待0.5秒。插入
timeout 1
命令以降低轮询率怎么样?这行得通吗?是的,行得通,但会减慢程序的反应,因为semaLock在等待另一个版本发布时平均会等待0.5秒thread@AdrianoRepetti:
start
命令没有任何等待另一进程终止的选项…@Aacini true,我只是重新阅读了这个问题,但我错过了要点(等待另一个进程,而不是第二批进程本身终止)@AdrianoRepetti:start命令没有任何选项可以等待另一个进程的终止…@Aacini true,我只是重新阅读了这个问题,我错过了要点(等待另一个进程,而不是第二批本身终止)