找回密码
 注册
搜索
[新手上路]批处理新手入门导读[视频教程]批处理基础视频教程[视频教程]VBS基础视频教程[批处理精品]批处理版照片整理器
[批处理精品]纯批处理备份&还原驱动[批处理精品]CMD命令50条不能说的秘密[在线下载]第三方命令行工具[在线帮助]VBScript / JScript 在线参考
查看: 88196|回复: 17

[系统相关] [已解决]批处理如何获取自身进程的PID?

[复制链接]
发表于 2013-1-18 13:24:32 | 显示全部楼层 |阅读模式
本帖最后由 BAT-VBS 于 2013-1-19 11:01 编辑

http://www.bathome.net/thread-4066-1-1.html
这个帖子里面的代码不靠谱,因为系统里面可能不止一个cmd.exe进程在运行。

评分

参与人数 1PB +2 收起 理由
Batcher + 2 感谢给帖子标题标注[已解决]字样

查看全部评分

发表于 2013-1-18 14:20:12 | 显示全部楼层
好像链接中有你想要的答案啊。。。

  1. @echo off
  2. set "mpath=%~0"
  3. wmic process where commandline='cmd /c ""%mpath:\=\\%" "' get processid
  4. pause>nul
复制代码
发表于 2013-1-18 14:21:20 | 显示全部楼层
本帖最后由 terse 于 2013-1-18 14:23 编辑

除非你多次运行 否则应该满足的
我的意思是 PATH 是单一的 就单一“PATH” 文件运行 应是唯一的
 楼主| 发表于 2013-1-18 17:06:00 | 显示全部楼层
回复 2# batman


C:\Test>test.bat
无可用范例。

XP SP3 原版系统
 楼主| 发表于 2013-1-18 17:07:31 | 显示全部楼层
回复 3# terse


太高深看不懂。
比如我随便打开一个cmd窗口,然后再双击运行test.bat,如果根据cmd.exe的进程来获取pid,很显然是会出错的吧。
发表于 2013-1-18 17:28:22 | 显示全部楼层
  1. wmic process where name="wmic.exe" get parentprocessid
复制代码
发表于 2013-1-18 20:08:56 | 显示全部楼层
回复 5# BAT-VBS
首先每次运行TEST.bat都将得到不同PID  运行一次 将得到TEST.bat进程 PID
你可以先运行名称非TEST的其他BAT文件
再运行TEST.bat  得到的仍是TEST.bat进程 PID
当然有另一情况  那就是 你连续运行两次以上TEST.bat  那你将得到多个 TEST.bat 进程 PID
以下内容为 TEST.bat
  1. @echo off
  2. set path_=%0
  3. for /f "usebackq skip=1" %%i in (`"wmic process where commandline='cmd /c "%path_:\=\\% "' get processID"`) do echo %%i
  4. pause
复制代码
 楼主| 发表于 2013-1-18 21:50:27 | 显示全部楼层
回复 7# terse


    测试结果见4楼,不知道是我的系统有问题,还是这个方法不通用。
 楼主| 发表于 2013-1-18 21:50:57 | 显示全部楼层
回复 6# CrLf


    版主V5
 楼主| 发表于 2013-1-18 22:10:02 | 显示全部楼层
我自己写了一个tasklist,不知道是否通用。
  1. @echo off
  2. for /f "tokens=2" %%a in ('tasklist /v ^| findstr /c:"- %0"') do (
  3.     echo %%a
  4. )
  5. pause
复制代码
 楼主| 发表于 2013-1-18 22:20:58 | 显示全部楼层
回复 6# CrLf


版主,我发现一个问题。把wmic放到bat文件里面之后,它获取的pid并非此bat的pid,是不是wmic在执行的时候自己会先创建一个子进程?
  1. @echo off
  2. for /f "tokens=2 delims==" %%a in ('wmic process where "name='wmic.exe'" get parentprocessid /value') do (
  3.     set "myPid=%%a"
  4. )
  5. echo,%myPid%
  6. pause
复制代码
发表于 2013-1-19 03:56:24 | 显示全部楼层
回复 11# BAT-VBS


    for /f 从命令中获取输入时,实际上是执行了一个 %comspec% /c xxxxxx,待进程退出后解析其输出,所以如果在 for /f 中执行 wmic 获得的将是 for /f 所创建的 cmd.exe 进程 pid。
    要想通过 for /f 获取当前进程 pid,在原方案的基础上有三个延伸方案
1、用临时文件避免产生多余进程
  1. wmic process where name="wmic.exe" get parentprocessid>tmp.txt
  2. for /f "skip=1" %%a in (tmp.txt) do echo %%a
复制代码
2、利用管道的特性,直接解析外部命令输出
  1. wmic process where name="wmic.exe" get parentprocessid|for /f "skip=1" %%a in ('more') do echo %%a
复制代码
3、先获取 for /f 产生的进程pid
  1. for /f "skip=1" %%a in ('"@for /f "skip=1" %%p in ('wmic process where name^="wmic.exe" get parentprocessid') do @wmic process where processid="%%p" get parentprocessid"') do echo %%a
复制代码
但是鉴于 wmic 无论在 xp 还是 win7 下输出都带有多余的回车符,所以建议在解析时这样过滤一下:
  1. for /f %%a in ('copy /z "%~0" nul') do set "回车符=%%a"
  2. for /f "delims=%回车符%" %%a in ("wmic的输出.txt") echo %%a
复制代码
除了通过父进程 pid 和 batman 以脚本路径为依据的办法,还可以通过标题栏来获取:
  1. set "title=%random%"
  2. title %title%
  3. tasklist /fi "windowtitle eq %title%"
  4. ::如果是以管理员权限运行的,则是 tasklist /fi "windowtitle eq 管理员:  %title%*"
复制代码

评分

参与人数 1技术 +1 收起 理由
BAT-VBS + 1 乐于助人

查看全部评分

 楼主| 发表于 2013-1-19 11:00:48 | 显示全部楼层
回复 12# CrLf


    感谢大神,学习了。
发表于 2013-1-19 13:36:06 | 显示全部楼层
2、利用管道的特性,直接解析外部命令输出
wmic process where name="wmic.exe" get parentprocessid|for /f "skip=1" %%a in ('more') do echo %%a ...
CrLf 发表于 2013-1-19 03:56


在管道后面使用 for 以前没想到。学习了。
发表于 2013-1-19 14:04:21 | 显示全部楼层
本帖最后由 terse 于 2013-1-22 15:47 编辑

总感觉 通过父进程得到pid 还是要确认路径的 才可靠

原来确定父进程pid是FOR输出是 for /f 所创建的 cmd.exe 进程 pid
所以错误的认为非路径确认 学习了 解析输出
所以 否定上面 “总感觉 通过父进程得到pid 还是要确认路径的 才可靠” !
您需要登录后才可以回帖 登录 | 注册

本版积分规则

Archiver|手机版|小黑屋|批处理之家 ( 渝ICP备10000708号 )

GMT+8, 2026-3-20 19:52 , Processed in 0.036495 second(s), 18 queries .

Powered by Discuz! X3.5

© 2001-2026 Discuz! Team.

快速回复 返回顶部 返回列表