用PowerShell解析/格式化字符串

问题描述:

这个original question不是关于PowerShell的。我假设这些基本前提:用PowerShell解析/格式化字符串

  • 我们运行的是Windows 7
  • 我们要分析的是Windows 7附带
  • 我们希望从输出提取有关网络适配器的信息和系统的系统信息工具的结果将其放入一些数据结构中以供进一步处理。

现在,我知道获取网卡信息比运行systeminfo和解析输出有更好的方法。我的兴趣不在于这个特定的实用工具。我正在考虑在PowerShell中解析/格式化一些文本的通用任务。我觉得powershell非常适合这类任务,也许比C#更好(取决于特定的要求)。这就是为什么我提供my answer PowerShell的原始问题。

我的问题,虽然是这样。我总觉得一些PowerShell的语法有点麻烦。 你会如何改进我的代码?请注意,代码不必在完全相同的结构中返回完全相同的结果。 我正在寻找可以帮助文本解析/处理的技巧。我一次又一次看到社区在处理大量任务方面的聪明才智。我已经看到了复杂问题的简单解决方案,直到有人告诉你如何解决这些问题一点都不明显。这就是我问的原因。

下面是代码:

所有的
$networkCards = systeminfo | ForEach-Object {$a=0} { 
    if ($_.startswith("Network Card(s)")) {$a=1} else {if ($a) {$_}} 
} 

$networkCards | ForEach-Object {[email protected]{}} { 
    if ($_.trim().startswith("[")) { 
     $c = $_.trim(); $data[$c] = @()} else {$data[$c] += $_.trim() 
    } 
} 

#Now we have a hash table with the keys as requested in the question 
#and the values are lists of separate strings, but those can be easily 
#concatenated if needed. Let's display it: 
$data 

我会在上面缓和:-)答案试试:

虽然Powershell的可以用来解析信息从例如systeminfo,有更好的信息接口。看看Get-WmiObject。在这种情况下,似乎想到了Get-WmiObject Win32_NetworkAdapterWin32_NetworkAdapterConfiguration。也有Win32_NetworkProtocolWin32_NetworkConnection,可能会给你你需要的信息。

结合Select-Object,Sort-ObjectFormat-Table来展示您所需要的数据。

+0

谢谢=)我了解WMI。我甚至明确表示,我知道在我的问题中有更好的方法来获取信息,因为我知道人们会建议WMI =)。这不是我现在感兴趣的东西。我只是用这个输出的systeminfo作为可能需要解析的文本的一个例子。 – 2011-05-19 09:11:08

+0

由于没有答案我回答我的问题,(这是因为问题的性质,真的),我想“关闭”这个问题,我选择一个,我认为这三个问题中最有用。 – 2011-05-22 21:45:02

首先,请停止使用PowerShell像往常一样的脚本语言。

PowerShell使用对象和解析字符串是绝对不是做你想做的事情的好方法。我必须修改你的脚本到我的语言来得到$ data的东西

对于我来说这里的东西没有任何意义,但是你构造了一个数组的哈希表,并且我给你开发它的方法。

所以使用$数据,你可以写:

foreach ($key in $data.keys) 
{ 
    write-Host ("The name is {0}, the value is {1}" -f $key, $data[$key]) 
} 

对我来说,它提供了:

The name is [02]: fe80::391a:2817:8f3e:6f2f, the value is System.Object[] 
The name is [02]: Intel(R) WiFi Link 5300 AGN, the value is System.Object[] 
The name is [02]: fe80::c70:cc38:cf64:eb27, the value is System.Object[] 
The name is [01]: 192.168.183.1, the value is System.Object[] 
The name is [01]: 192.168.0.3, the value is System.Object[] 
The name is [03]: VMware Virtual Ethernet Adapter for VMnet1, the value is System.Object[] 
The name is [05]: Microsoft Virtual WiFi Miniport Adapter, the value is System.Object[] 
The name is [02]: fe80::5d48:c4a:5987:ee73, the value is System.Object[] 
The name is [04]: VMware Virtual Ethernet Adapter for VMnet8, the value is System.Object[] 
The name is [01]: 192.168.234.1, the value is System.Object[] 
The name is [01]: Intel(R) 82567LM Gigabit Network Connection, the value is System.Object[] 

因为$数据[$关键]是一个数组。你可以这样写:

foreach ($key in $data.keys) 
{ 
    write-Host ("The name is {0}" -f $key) 
    foreach($line in $data[$key]) 
    { 
    Write-Host ("`t$line") 
    } 
} 

对我来说,它提供了:

The name is [02]: fe80::391a:2817:8f3e:6f2f 
The name is [02]: Intel(R) WiFi Link 5300 AGN 
    Nom de la connexion : Connexion réseau sans fil 
    État :    Support déconnecté 
The name is [02]: fe80::c70:cc38:cf64:eb27 
The name is [01]: 192.168.183.1 
The name is [01]: 192.168.0.3 
The name is [03]: VMware Virtual Ethernet Adapter for VMnet1 
    Nom de la connexion : VMware Network Adapter VMnet1 
    DHCP activé :   Non 
    Adresse(s) IP 
The name is [05]: Microsoft Virtual WiFi Miniport Adapter 
    Nom de la connexion : Connexion réseau sans fil 2 
    État :    Support déconnecté 
The name is [02]: fe80::5d48:c4a:5987:ee73 
The name is [04]: VMware Virtual Ethernet Adapter for VMnet8 
    Nom de la connexion : VMware Network Adapter VMnet8 
    DHCP activé :   Non 
    Adresse(s) IP 
The name is [01]: 192.168.234.1 
The name is [01]: Intel(R) 82567LM Gigabit Network Connection 
    Nom de la connexion : Connexion au réseau local 
    DHCP activé :   Oui 
    Serveur DHCP :  192.168.0.254 
    Adresse(s) IP 
+0

谢谢你的贡献。您能否详细说明一下“首先,请停止使用Powershell作为通常的脚本语言”。我完全和完全不明白你的意思。 – 2011-05-19 07:53:08

+0

当你需要一个信息。在Powershel中,游戏是要找到对象(来自CmdLets或大部分时间.NET类),这些对象会根据他的属性或方法提供给你。 WMI也是一个很好的提供商。 – JPBlanc 2011-05-19 08:15:30

+0

我对Powershell是什么类型的语言非常熟悉,不过谢谢你=) – 2011-05-19 08:36:21

大家都在谈论物体是否正确。这个想法是将一个对象从一个方法直接发送到另一个方法,然后对该对象进行操作。我不是PS上的大师,但我开始明白这个主意。希望这个脚本能够让你向前迈进一点。

$text = @" 
key1:value1 
key2:value2 
key3:value3 
"@ 
$map = @{} 
($text -split "`n") | Where-Object {$_ -imatch 'key2'} | foreach-object {$tokens = $_ -split ":"; $map.Add($tokens[0],$tokens[1])} 
$map 
+0

这与我在我的例子中所做的很相似,我想呢?还是有一个你正在使用的概念,我忽略了? – 2011-05-19 20:41:00