Windows中VB.NET如何关联网卡接口信息与性能计数器数据
问题:关联网卡基本信息与性能计数器发送速率
我通过VB.NET代码获取了所有网卡的名称、描述及最大速度:
Dim AllNetworkInterfaces() As System.Net.NetworkInformation.NetworkInterface = System.Net.NetworkInformation.NetworkInterface.GetAllNetworkInterfaces For Each ThisNI As NetworkInterface In AllNetworkInterfaces Console.WriteLine(ThisNI.Name & " " & ThisNI.Speed & " " & ThisNI.Description) Next
输出示例:
Name Speed Description
"Media Network 10Gb" 100000000 "Intel Ethernet Connection Adapter #2"
同时我也获取了各网卡的bytes sent/sec性能计数器数据,示例如下:
"Instance Name" "bytes send/sec"
"Intel Ethernet Connection Adapter _2" 176.5
现在需要同时展示网卡名称、描述、最大速度及实际发送速率,但两者无法直接关联:网卡描述中的#在性能计数器实例名中变为_,且性能计数器未返回网卡真实名称。
解决方法
方法1:通过WMI直接关联所有数据(推荐)
使用WMI可以一次性获取网卡的真实名称、描述、最大速度和发送速率,无需手动处理标识转换,避免匹配错误。
Imports System.Management Module NetworkMonitor Sub Main() ' 第一步:获取网卡真实名称(NetConnectionID)与InterfaceIndex的映射 Dim nicRealNameMap As New Dictionary(Of UInt32, String)() Dim nicQuery As New ObjectQuery("SELECT NetConnectionID, InterfaceIndex FROM Win32_NetworkAdapter WHERE NetConnectionID IS NOT NULL") Dim nicSearcher As New ManagementObjectSearcher(nicQuery) For Each nicObj As ManagementObject In nicSearcher.Get() Dim interfaceIndex As UInt32 = UInt32.Parse(nicObj("InterfaceIndex").ToString()) Dim realName As String = nicObj("NetConnectionID").ToString() nicRealNameMap(interfaceIndex) = realName Next ' 第二步:获取性能数据并关联真实名称 Dim perfQuery As New ObjectQuery("SELECT InterfaceIndex, Description, Speed, BytesPersecSent FROM Win32_PerfFormattedData_Tcpip_NetworkInterface") Dim perfSearcher As New ManagementObjectSearcher(perfQuery) For Each perfObj As ManagementObject In perfSearcher.Get() Dim interfaceIndex As UInt32 = UInt32.Parse(perfObj("InterfaceIndex").ToString()) Dim realName As String = If(nicRealNameMap.ContainsKey(interfaceIndex), nicRealNameMap(interfaceIndex), "未知网卡") Console.WriteLine($"真实名称: {realName}") Console.WriteLine($"描述: {perfObj("Description")}") Console.WriteLine($"最大速度: {If(perfObj("Speed") Is DBNull.Value, "未知", perfObj("Speed"))}") Console.WriteLine($"发送速率(字节/秒): {perfObj("BytesPersecSent")}") Console.WriteLine("----------------------------------------") Next End Sub End Module
方法2:手动处理标识替换并关联(兼容旧场景)
如果必须使用NetworkInterface类和性能计数器,可以通过替换描述中的#为_来匹配,但需注意重复描述的情况:
Imports System.Net.NetworkInformation Imports System.Diagnostics Module NetworkMonitor Sub Main() ' 存储网卡信息,Key为替换后的描述(匹配性能计数器实例名) Dim nicMap As New Dictionary(Of String, NetworkInterface)() Dim allNics() As NetworkInterface = NetworkInterface.GetAllNetworkInterfaces() For Each nic In allNics ' 将描述中的#替换为_,匹配性能计数器实例名格式 Dim perfInstanceName As String = nic.Description.Replace("#", "_") nicMap(perfInstanceName) = nic Next ' 获取性能计数器数据 Dim perfCategory As New PerformanceCounterCategory("Network Interface") Dim instanceNames() As String = perfCategory.GetInstanceNames() For Each instanceName In instanceNames If nicMap.ContainsKey(instanceName) Then Dim nic = nicMap(instanceName) Dim bytesSentCounter As New PerformanceCounter("Network Interface", "Bytes Sent/sec", instanceName) Console.WriteLine($"真实名称: {nic.Name}") Console.WriteLine($"描述: {nic.Description}") Console.WriteLine($"最大速度: {nic.Speed}") Console.WriteLine($"发送速率(字节/秒): {bytesSentCounter.NextValue()}") Console.WriteLine("----------------------------------------") End If Next End Sub End Module
注意:方法2存在风险,如果多个网卡描述仅
#后的数字不同,替换后可能出现重复实例名,导致匹配错误,因此优先推荐方法1。
内容的提问来源于stack exchange,提问作者Sam Marrocco
相关产品推荐
相关产品推荐

