【问题标题】:How to read an XML file using PowerShell and filter the required data如何使用 PowerShell 读取 XML 文件并过滤所需数据
【发布时间】:2019-05-10 16:13:28
【问题描述】:

如何使用 PowerShell 读取 XML 文件并从具有大量标签的文件中提取数据?我正在使用以下代码提取标签,但无法从子标签中读取数据。

$xmlFile= "D:\Testing\TestcasesOutput\1ac.xml"
$xmlConfig = [System.Xml.XmlDocument](Get-Content $xmlFile)
$XmlDocument.Breakfast_menu.price

我希望输出读取整个 xml 文件,但无法读取整个 xml 文件。

<?xml version="1.0" encoding="UTF-8"?>
<breakfast_menu>
    <food>
        <food>Belgian Waffles</food>
        <price>$5.95</price>
        <description>Two of our famous Belgian Waffles with plenty of real maple 
        syrup</description>
        <calories>650</calories>
    </food>
    <food>
        <food>Strawberry Belgian Waffles</food>
        <price>$7.95</price>
        <description>Light Belgian waffles covered with strawberries and whipped 
        cream</description>
        <calories>900</calories>
    </food>
    <food>
        <food>Berry-Berry Belgian Waffles</food>
        <price>$8.95</price>
        <description>Light Belgian waffles covered with an assortment of fresh 
        berries and whipped cream</description>
        <calories>900</calories>
    </food>
    <food>
        <food>French Toast</food>
        <price>$4.50</price>
        <description>Thick slices made from our homemade sourdough 
        bread</description>
        <calories>600</calories>
    </food>
    <food>
    <food>Homestyle Breakfast</food>
        <price>$6.95</price>
        <description>Two eggs, bacon or sausage, toast, and our ever-popular hash 
        browns</description>
        <calories>950</calories>
    </food>
</breakfast_menu>

【问题讨论】:

  • 我正在使用下面的代码来提取早餐菜单标签,但无法从早餐菜单子标签中读取数据。 $xmlFile= "D:\Testing\TestcasesOutput\1ac.xml" $xmlConfig = [System.Xml.XmlDocument](Get-Content $xmlFile) $XmlDocument.Breakfast_menu.price
  • 不要评论你自己的问题,而是将这些重要的行附加到它上面。
  • edit您的问题并将xml(的相关部分)放在那里。接下来,同上@quantummind cmets
  • @Theo 比利时华夫饼$5.95两个我们著名的比利时华夫饼配大量真正的枫糖浆650
  • 恐怕这不是一个诺诺。如评论所述,单击您的问题下方的edit,然后将信息放入formatted way。切勿在评论中粘贴重要信息或代码,因为这很快就会变得难以阅读。

标签: xml powershell


【解决方案1】:

使用 PowerShell 读取 XML 非常简单。

假设你的 xml 文件看起来像这样:

<?xml version="1.0" encoding="UTF-8"?> 
<breakfast_menu> 
    <food> 
        <food>Belgian Waffles</food>
        <price>$5.95</price>
        <description>Two of our famous Belgian Waffles with plenty of real maple syrup</description>
        <calories>650</calories>
    </food>
    <food> 
        <food>Fried Egg</food>
        <price>$1.80</price>
        <description>blahblah</description>
        <calories>3500</calories>
    </food>
</breakfast_menu>

您只需读取文件并让 PowerShell 使用此方法将文件解析为对象

[xml]$xml = Get-Content 'D:\Testing\TestcasesOutput\1ac.xml'

接下来,您可以使用此$xml 对象的属性来获取您想要从中提取的任何内容:

比如循环遍历所有&lt;food&gt;项目,输出你想要的信息

$xml.breakfast_menu.food | ForEach-Object {
    [PSCustomObject]@{
        'MenuItem' = $_.food
        'Price'    = $_.price
    }
}

结果如下:

MenuItem        Price
--------        -----
Belgian Waffles $5.95
Fried Egg       $1.80

或者只选择“比利时华夫饼”项:

$xml.breakfast_menu.food | Where-Object { $_.food -eq 'Belgian Waffles' } | 
                           Select-Object @{Name = 'MenuItem'; Expression = {$_.food}}, Price

输出:

MenuItem        price
--------        -----
Belgian Waffles $5.95

如果您只追求某种食品的价格,您可以这样做:

$xml.breakfast_menu.food | Where-Object { $_.food -eq 'Belgian Waffles' } | 
                           Select-Object -ExpandProperty Price

甚至缩短该代码:

($xml.breakfast_menu.food | Where-Object { $_.food -eq 'Belgian Waffles' }).price

希望能解释一下


编辑

如果您需要对多个 xml 文件执行此操作,并且这些文件位于 same 根路径中,您可以使用 Get-ChildItem 循环获取 xml 文件并像示例中一样处理它们我给了。

Get-ChildItem -Path 'ROOTFOLDER OF THE FOLDERS WHERE THE XML FILES ARE KEPT' -Filter '*.xml' -File -Recurse | 
    ForEach-Object {
        [xml]$xml = Get-Content -Path $_.FullName
        # in this example simply output the menu items and their price for each xml file
        foreach ($item in $xml.breakfast_menu.food) {
            [PSCustomObject]@{
                'File'     = $_.FullName    # added the file FullName so you know where the item came from
                'MenuItem' = $item.food
                'Price'    = $item.price
            }
        }
    }

或来自多个位置:

$folders = 'D:\Testing\TestcasesOutput\1ac7b5a0-2d62-403c-8394-5bd33330cbe7',
           'D:\Testing\TestcasesOutput\227c619a-b7d1-4da6-8fe5-f2c923ddcb7a',
           'D:\Testing\TestcasesOutput\d4370ae1-643f-4c44-ba41-7f640afcc276'

$result = Get-ChildItem -Path $folders -Filter '*.xml' -File | 
    ForEach-Object {
        [xml]$xml = Get-Content -Path $_.FullName
        # in this example simply output the menu items and their price for each xml file
        foreach ($item in $xml.breakfast_menu.food) {
            [PSCustomObject]@{
                'File'     = $_.FullName
                'MenuItem' = $item.food
                'Price'    = $item.price
            }
        }
    }

#output to screen:
$result

# output to CSV
$result | Export-Csv -Path 'PATH AND FILENAME FOR THE OUTPUT CSV FILE' -NoTypeInformation

【讨论】:

  • 是的,它有很大帮助,但我有另一个 xml 文件,它有 3000 行,通过使用与您描述的相同的方法,我解析了数据但无法获取它。您能否确认大型 xml 文件是否存在问题?
  • @Ali 3000行应该没问题..仔细研究结构。是不是和这个xml一样,只是更大一些?
  • 感谢您的支持。您能否进一步解释如何解析位于路径中的 100xml 文件并 grep 所需的数据并删除剩余的数据。如果您进一步指导我会非常有帮助??
  • 通过使用以下脚本,我可以处理单个 xml 文件 [xml]$xmlDocument= Get-Content -Path "D:\Testing\TestcasesOutput\1ac\Export25.xml" $xmlConfig = [System.Xml.XmlDocument](Get-Content $xmlFile) $xmlDocument.Content.sessionEventTypeItem
  • 但是当我尝试处理 100 个 xml 文件时,它不显示输出。 [xml]$xmlDocument= 获取内容-路径 "D:\Testing\TestcasesOutput\1ac\Export25.xml" $xmlConfig = [System.Xml.XmlDocument](获取内容 $xmlFile) $xmlDocument.Content.sessionEventTypeItem跨度>
猜你喜欢
  • 1970-01-01
  • 2020-09-04
  • 2010-12-21
  • 2019-09-19
  • 1970-01-01
  • 2010-11-19
  • 1970-01-01
  • 2014-01-18
  • 2014-04-25
相关资源
最近更新 更多