Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/powershell/12.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
当某些属性丢失时,如何将XML转换为对象? 问题_Xml_Powershell - Fatal编程技术网

当某些属性丢失时,如何将XML转换为对象? 问题

当某些属性丢失时,如何将XML转换为对象? 问题,xml,powershell,Xml,Powershell,我正在尝试将位置的XML列表转换为一组对象 XML文件的每个位置都有一个Location元素。XML属性包含对象属性值 我希望某些目标属性的名称与源属性的名称不同 稍后我想将对象序列化为CSV文件,因此属性的顺序很重要 以下是两个位置的示例来说明问题: [xml] $InputXml = @' <?xml version="1.0" encoding="UTF-8"?> <CTLocations xmlns="http://www.cartrawler.com/"> &

我正在尝试将位置的XML列表转换为一组对象

XML文件的每个位置都有一个Location元素。XML属性包含对象属性值

我希望某些目标属性的名称与源属性的名称不同

稍后我想将对象序列化为CSV文件,因此属性的顺序很重要

以下是两个位置的示例来说明问题:

[xml] $InputXml = @'
<?xml version="1.0" encoding="UTF-8"?>

<CTLocations xmlns="http://www.cartrawler.com/">
<Country code="AL" name="Albania" continent="Europe">
<Location Id="7188" Name="Tirana Airport" Lat="41.42108838" Lng="19.71271276" CountryCode="AL" Address="Tirana Airport Muhamet Gjollesha Str., Muhamet Gjollesha Str., Tirana" CityName="Tirana" Airport="1" AirportCode="TIA" RailwayStation="0"/>
<Location Id="30768" Name="Tirana Downtown" Lat="41.332" Lng="19.832" CountryCode="AL" Address="Rruga E Durresit. Nr 61, Tirana" CityName="Tirana" Airport="0" RailwayStation="0"/>
</Country>
</CTLocations>
'@
严格模式结果 当我设置了严格模式时:

Set-StrictMode -Version 3.0
第一个元素包含所有属性,因此转换为对象:

LocationCode         : 7188
LocationName         : Tirana Airport
Latitude             : 41.42108838
Longitude            : 19.71271276
CountryCode          : AL
FormattedAddress     : Tirana Airport Muhamet Gjollesha Str., Muhamet Gjollesha Str., Tirana
CityName             : Tirana
ServesAirport        : 1
AirportCode          : TIA
ServesRailwayStation : 0
第二个元素缺少AirportCode属性,因此PowerShell会引发异常:

Property 'AirportCode' cannot be found on this object. Make sure that it exists.
At line:16 char:3
+   [PSCustomObject] @{
+   ~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : NotSpecified: (:) [], PropertyNotFoundException
    + FullyQualifiedErrorId : PropertyNotFoundStrict
非ICT模式结果 当我关闭严格模式时:

Set-StrictMode -Off
PowerShell将这两个位置都转换为对象。缺少的属性为空:

LocationCode         : 7188
LocationName         : Tirana Airport
Latitude             : 41.42108838
Longitude            : 19.71271276
CountryCode          : AL
FormattedAddress     : Tirana Airport Muhamet Gjollesha Str., Muhamet Gjollesha Str., Tirana
CityName             : Tirana
ServesAirport        : 1
AirportCode          : TIA
ServesRailwayStation : 0

LocationCode         : 30768
LocationName         : Tirana Downtown
Latitude             : 41.332
Longitude            : 19.832
CountryCode          : AL
FormattedAddress     : Rruga E Durresit. Nr 61, Tirana
CityName             : Tirana
ServesAirport        : 0
AirportCode          : 
ServesRailwayStation : 0
有更好的办法吗? 如果有更好的方法,我不想关闭严格模式来实现这一点


任何在严格模式下工作的东西都是可以接受的。我一直在找一个像,或者。也许还有一种XPath方法可以做到这一点。

在您的情况下,这很简单:

select-Xml -Xml $InputXml -XPath '//ns:Location' -Namespace @{ns = 'http://www.cartrawler.com/'} |
% {
  $n = $_.Node

  [PSCustomObject] @{
    LocationCode = $n.Id
    LocationName = $n.Name
    Latitude = $n.Lat
    Longitude = $n.Lng
    CountryCode = $n.CountryCode
    FormattedAddress = $n.Address
    CityName = $n.CityName
    ServesAirport = $n.Airport
    AirportCode = $(if($n.Airport -eq '1'){$n.AirportCode}else{""})
    ServesRailwayStation = $n.RailwayStation
  }
}
更一般地说:

select-Xml -Xml $InputXml -XPath '//ns:Location' -Namespace @{ns = 'http://www.cartrawler.com/'} |
% {
  $n = $_.Node

  [PSCustomObject] @{
    LocationCode = $n.Id
    LocationName = $n.Name
    Latitude = $n.Lat
    Longitude = $n.Lng
    CountryCode = $n.CountryCode
    FormattedAddress = $n.Address
    CityName = $n.CityName
    ServesAirport = $n.Airport
    AirportCode = $(if($n.GetAttributeNode("AirportCode") -ne $null){$n.AirportCode}else{""})
    ServesRailwayStation = $n.RailwayStation
  }
}

一旦写下,我的旧程序员意见(你不在乎)就是如果你想使用严格的模式,就停止脚本编写,开始写java、C、C或C++。您正在与strict mode进行斗争的近似方法是+脚本编程,这对我来说可以很快地解决表角的一个问题。我的观点是,使用严格模式带来了传统编程的所有缺点,但这只是我的观点。

在您的情况下,很容易:

select-Xml -Xml $InputXml -XPath '//ns:Location' -Namespace @{ns = 'http://www.cartrawler.com/'} |
% {
  $n = $_.Node

  [PSCustomObject] @{
    LocationCode = $n.Id
    LocationName = $n.Name
    Latitude = $n.Lat
    Longitude = $n.Lng
    CountryCode = $n.CountryCode
    FormattedAddress = $n.Address
    CityName = $n.CityName
    ServesAirport = $n.Airport
    AirportCode = $(if($n.Airport -eq '1'){$n.AirportCode}else{""})
    ServesRailwayStation = $n.RailwayStation
  }
}
更一般地说:

select-Xml -Xml $InputXml -XPath '//ns:Location' -Namespace @{ns = 'http://www.cartrawler.com/'} |
% {
  $n = $_.Node

  [PSCustomObject] @{
    LocationCode = $n.Id
    LocationName = $n.Name
    Latitude = $n.Lat
    Longitude = $n.Lng
    CountryCode = $n.CountryCode
    FormattedAddress = $n.Address
    CityName = $n.CityName
    ServesAirport = $n.Airport
    AirportCode = $(if($n.GetAttributeNode("AirportCode") -ne $null){$n.AirportCode}else{""})
    ServesRailwayStation = $n.RailwayStation
  }
}

一旦写下,我的旧程序员意见(你不在乎)就是如果你想使用严格的模式,就停止脚本编写,开始写java、C、C或C++。您正在与strict mode进行斗争的近似方法是+脚本编程,这对我来说可以很快地解决表角的一个问题。我的观点是,使用严格模式带来了传统编程的所有缺点,但这只是我的观点。

($n |选择AirportCode)。AirportCode是一个可接受的解决方案?是
($n |选择AirportCode)。AirportCode是一个可接受的解决方案?一个“啊哈!”的时刻。我希望我有类似的东西。
$(if(){}else{})
似乎是PowerShell的等价物。我重视您的意见。严格模式当然有捕捉意外错误的地方,但我不应该对此感到困扰。我更喜欢非ICT解决方案的优雅,它正是我想要的,而且更容易理解。感谢您向我演示如何严格执行此操作,但最后我可能会更好地放宽语法。@I如果您愿意的话。这是否仍然会导致引发相同的异常?在我的测试中不是这样的。你有例外吗?一个“啊哈”的时刻。我希望我有类似的东西。
$(if(){}else{})
似乎是PowerShell的等价物。我重视您的意见。严格模式当然有捕捉意外错误的地方,但我不应该对此感到困扰。我更喜欢非ICT解决方案的优雅,它正是我想要的,而且更容易理解。感谢您向我演示如何严格执行此操作,但最后我可能会更好地放宽语法。@I如果您愿意的话。这是否仍然会导致引发相同的异常?在我的测试中不是这样的。你有例外吗?