
标题: [系统相关] bat调用vbs代码,检测显示磁盘序号是什么规则? [打印本页]
作者: ygqiang 时间: 2025-3-22 07:05 标题: bat调用vbs代码,检测显示磁盘序号是什么规则?
本帖最后由 ygqiang 于 2025-3-25 06:33 编辑
bat调用vbs代码,检测显示磁盘序号是什么规则?
不同的主机,显示的磁盘序号顺序:
有时候是: 4,3, 1 ,2 ,0, 5
有时候是:0,4,2,3,1。
有时候是:1,0。
有时候是:0,1。
有时候是:2,0,1。
主要要求:磁盘序号按顺序显示。并且分区表格式(GPT或MBR)显示正确。
下面这个vbs代码,分区表格式(GPT或MBR)显示正常。
问题是:磁盘序列号排列会乱序。



- @echo off
-
-
- echo.
- echo.
-
- (
- echo list disk
- echo exit
- ) | diskpart
-
-
- ping 0 -n 5 >nul 2>nul
-
- echo.
- echo.
-
- cscript //Nologo 引导方式-硬盘格式.vbs
-
- echo.
- echo.
-
- ping 0 -n 12 >nul 2>nul
-
- exit
复制代码
- Set ws = CreateObject("Wscript.Shell")
- Set fso = CreateObject("Scripting.FileSystemObject")
-
- If LCase(Right(WSH.FullName, 11)) = "wscript.exe" Then
- ws.run "cscript.exe -nologo """ & WSH.ScriptFullName & """", 0
- WSH.Quit
- End If
-
- Dim arr()
- Set oExec = ws.Exec("cmd /c ""(echo;list disk|diskpart)|findstr /irc:""[0-9][0-9]* *[tgmk]b"" "" ")
-
- Do While oExec.StdOut.AtEndOfStream <> true
- str = Trim(oExec.StdOut.ReadLine)
- num = CInt(Split(str, " ")(1))
- ReDim Preserve arr(num)
- If InStrRev(str, "*") >0 Then
- arr(num) = "GPT"
- Else
- arr(num) = "MBR"
- End If
- Loop
-
- Dim objWMI, colDisks
- Set objWMI = GetObject("winmgmts:\\.\root\cimv2")
- Set colDisks = objWMI.ExecQuery("select * from Win32_DiskDrive where MediaType like 'fixed%'")
- For Each objDisk in colDisks
- s = s & "硬盘" & objDisk.Index & ":" & vbTab
- s = s & "大小:" & GetSize(objDisk.Size) & vbTab
- s = s & "型号:" & objDisk.Caption & vbTab
- s = s & "分区表:" & arr(CInt(objDisk.Index)) & vbCrLf
- strDiskID = Replace(objDisk.DeviceID, "\", "\\")
- Set colPartitions = objWMI.ExecQuery _
- ("ASSOCIATORS OF {Win32_DiskDrive.DeviceID=""" & strDiskID & """}" _
- & " where AssocClass=Win32_DiskDriveToDiskPartition")
- For Each objPartition in colPartitions
- strPartId = objPartition.DeviceID
- Set colLogicalDisks = objWMI.ExecQuery _
- ("ASSOCIATORS OF {Win32_DiskPartition.DeviceID=""" & strPartId & """} where AssocClass=Win32_LogicalDiskToPartition")
- For Each objLogicalDisk in colLogicalDisks
- size = objLogicalDisk.Size
- free = objLogicalDisk.Freespace
- used = FormatNumber((size - free) / size * 100, 2, true) & "%"
- s = s & "分区" & objLogicalDisk.DeviceID & vbTab
- s = s & "大小:" & GetSize(size) & vbTab
- s = s & "剩余:" & GetSize(free) & vbTab
- s = s & "使用率:" & used & vbCrLf
- Next
- Next
- s = s & vbCrLf
- Next
- 'Msgbox s
- WScript.Echo s
-
-
- Function GetSize(intSize)
- If intSize/1024/1024 > 1024 Then
- GetSize = FormatNumber(intSize/1024/1024/1024, 2, true) & "GB"
- Else
- GetSize = FormatNumber(intSize/1024/1024, 2, true) & "MB"
- End If
- End Function
复制代码
作者: ygqiang 时间: 2025-3-23 07:47
本帖最后由 ygqiang 于 2025-3-25 06:29 编辑
下面这个vbs代码,磁盘序列号显示正常,比如磁盘0、磁盘1、磁盘2....
问题是:分区表如果是GPT格式的,会错误的识别成MBR。
cscript //Nologo diskinfo.vbs- Main
- Sub Main()
- Dim objWMI, colDisks
- Set objWMI = GetObject("winmgmts:\\.\root\cimv2")
- Set colDisks = objWMI.ExecQuery("select * from Win32_DiskDrive where MediaType like 'fixed%'")
- ' 获取硬盘最大序号
- nIndexMax = 0
- For Each objDisk in colDisks
- If Cint(objDisk.Index) > nIndexMax Then nIndexMax = Cint(objDisk.Index)
- Next
- ' 按序号取信息
- For i = 0 To nIndexMax
- For Each objDisk in colDisks
- ' 只取该序号信息
- If objDisk.Index = i Then
- s = s & "硬盘" & objDisk.Index & ":" & vbTab
- s = s & "大小:" & GetSize(objDisk.Size) & vbTab
- 's = s & "型号:" & objDisk.Caption & vbCrLf
- s = s & "型号:" & objDisk.Caption & vbTab
- s = s & "分区表:" & IsGPT(objDisk.Index) & vbCrLf
- strDiskID = Replace(objDisk.DeviceID, "\", "\\")
- Set colPartitions = objWMI.ExecQuery _
- ("ASSOCIATORS OF {Win32_DiskDrive.DeviceID=""" & strDiskID & """}" _
- & " where AssocClass=Win32_DiskDriveToDiskPartition")
- For Each objPartition in colPartitions
- strPartId = objPartition.DeviceID
- Set colLogicalDisks = objWMI.ExecQuery _
- ("ASSOCIATORS OF {Win32_DiskPartition.DeviceID=""" & strPartId _
- & """} where AssocClass=Win32_LogicalDiskToPartition")
- For Each objLogicalDisk in colLogicalDisks
- size = objLogicalDisk.Size
- free = objLogicalDisk.Freespace
- used = FormatNumber((size - free) / size * 100, 2, true) & "%"
- s = s & "分区" & objLogicalDisk.DeviceID & vbTab
- s = s & "大小:" & GetSize(size) & vbTab
- s = s & "剩余:" & GetSize(free) & vbTab
- s = s & "使用率:" & used & vbCrLf
- Next
- Next
- s = s & vbCrLf
- End If
- Next
- Next
-
- WScript.Echo s
- End Sub
-
- ' 格式化
- Function GetSize(intSize)
- If intSize/1024/1024 > 1024 Then
- GetSize = FormatNumber(intSize/1024/1024/1024, 2, true) & "GB"
- Else
- GetSize = FormatNumber(intSize/1024/1024, 2, true) & "MB"
- End If
- End Function
-
- ' 获取指定硬盘的分区表类型(GPT/MBR)
- Function IsGPT(ByVal nDiskIndex)
- IsGPT = "MBR"
- Dim wso, sLogFile, sText
- Set wso = CreateObject("WScript.Shell")
- sLogFile = wso.ExpandenVironmentStrings("%temp%\diskpart.log")
- wso.Run "cmd /c ""chcp 437 & cls & (echo list disk | diskpart | find /i ""Disk " & nDiskIndex & """) >""" & sLogFile & """ "" ", 0, False
- Call TxtFile(sLogFile, 1, -2, sText)
- If Trim(Right(sText,3)) = "*" Then IsGPT = "GPT"
- End Function
-
- ' 对文本指定编码进行读写操作2
- 'nRW: 1只读, 2只写, 8追加 'nCharset: -2(系统), -1(Unicode), 0(ASCII)
- Sub TxtFile(ByVal FileName, ByVal nRW, ByVal nCharset, ByRef sText)
- Dim fso : Set fso = CreateObject("Scripting.filesystemobject")
- If sText <> "" And (nRW = 2 Or nRW = 8) Then
- fso.OpenTextFile(FileName, nRW, True, nCharset).Write sText
- ElseIf fso.FileExists(FileName) And nRW = 1 Then
- If fso.GetFile(FileName).Size > 0 Then _
- sText = fso.OpenTextFile(FileName, nRW, False, nCharset).ReadAll
- End If
- End Sub
-
- ' 以管理员身份运行
- Sub RunAsAdmin()
- Dim objItems, objItem, strVer, nVer
- Set objItems = GetObject("winmgmts:").InstancesOf("Win32_OperatingSystem")
- For Each objItem In objItems
- strVer = objItem.Version
- Next
- nVer = Split(strVer, ".")(0) & Split(strVer, ".")(1)
- If nVer >= 60 Then
- Dim oShell, oArg, strArgs
- Set oShell = CreateObject("Shell.Application")
- If Not WScript.Arguments.Named.Exists("ADMIN") Then
- For Each oArg In WScript.Arguments
- strArgs = strArgs & " """ & oArg & """"
- Next
- strArgs = strArgs & " /ADMIN:1"
- Call oShell.ShellExecute("WScript.exe", """" & WScript.ScriptFullName & """" & strArgs, "", "runas", 1)
- Set oShell = Nothing
- WScript.Quit(0)
- End If
- Set oShell = Nothing
- End If
- End Sub
复制代码
作者: Five66 时间: 2025-3-23 09:13
识别顺序???
主板插槽顺序???
作者: ygqiang 时间: 2025-3-23 09:17
本帖最后由 ygqiang 于 2025-3-23 09:31 编辑
识别顺序???
主板插槽顺序???
Five66 发表于 2025-3-23 09:13 
计算机管理-磁盘管理,根据这里显示的磁盘序号情况。
1、简单情况下:
直接按照序号显示磁盘情况,比如固定显示:0,1,2,3,4...
2、精确情况下:
首先显示系统盘。然后按照顺序显示其它盘。
比如,总共4个磁盘。
如果系统盘是磁盘1,其它磁盘显示顺序就是0,2,3
如果系统盘是磁盘2,其它磁盘显示顺序就是0,1,3
作者: Five66 时间: 2025-3-23 09:41
回复 4# ygqiang
2个盘 ,看了下 ,系统盘确实最先
不过直接按照序号不知道是啥序号
作者: ygqiang 时间: 2025-3-23 09:52
回复 5# Five66
1楼代码对比测试下,
diskpart命令就是按照顺序显示磁盘:0,1,2,3。。。
如果调用vbs代码,就不一定了,看不出是什么显示规律。
作者: ygqiang 时间: 2025-3-23 09:54
回复 5# Five66
序号就是,磁盘管理,这里显示的:磁盘0,磁盘1,磁盘2,磁盘3.....
作者: aloha20200628 时间: 2025-3-24 10:53
本帖最后由 aloha20200628 于 2025-3-24 11:07 编辑
回复 4# ygqiang
满足第二种情况的全部驱动器标识号列表(系统盘号置顶)且不必等候每个外接驱动器热连接》
一。系统盘符可直接从系统变量 %systemDrive% 取值
二。用 wmic 方法获取指定盘符对应的驱动器标识号
三。用 wmic+sort 方法获取全部驱动器标识号并予排序- @echo off &for /f "tokens=2 delims=#," %%x in (
- ' "wmic logicaldisk where DeviceID='%systemDrive%' assoc /assocclass:Win32_LogicalDiskToPartition" '
- ) do echo,%%x&for /f %%i in ('wmic diskdrive get index^|findstr /br [0-9]^|sort') do if %%i neq %%x echo,%%i
- pause&exit/b
复制代码
作者: ygqiang 时间: 2025-3-24 12:21
回复 8# aloha20200628
新版win11系统,好像不支持wmic了?
作者: aloha20200628 时间: 2025-3-24 12:49
回复 9# ygqiang
虽没有预装 win11,但用 DS ‘深度思考’ 的结论是 ‘目前的 win11 依然可用 wmic’,即使已被标记将被 ‘弃用’ ... 不过话说回来,vbs 早在 win11 问世时不就被 MS 宣布 ‘弃用’ 了吗
...
作者: ygqiang 时间: 2025-3-24 14:15
回复 10# aloha20200628
找了台win11 24h2系统,确实无法运行wmic了。
vbs代码是可以运行的。
作者: aloha20200628 时间: 2025-3-24 15:28
回复 11# ygqiang
参考此链接》如何在 win11 24H2 系统下重启 wmic 功能的两个方法 https://blog.csdn.net/wenzhongxiang/article/details/145956387
作者: ygqiang 时间: 2025-3-24 20:52
回复 12# aloha20200628
重新发布了另一个帖子,谢谢
欢迎光临 批处理之家 (http://www.bathome.net/) |
Powered by Discuz! 7.2 |