Reputation: 3109
I have this script:
function f3
{
[xml]$xml = @"
<?xml version="1.0" encoding="utf-8"?>
<Book>
<projects>
<project name="Book1" date="2009-01-20">
<editions>
<edition language="English">Novel_1</edition>
<edition language="English">my.Book1.com</edition>
<edition language="German">Ge.Book1.Com</edition>
<edition language="French">Fr.Book1.com</edition>
<edition language="Polish">Pl.Book1.com</edition>
<edition language="English">Novel_2</edition>
<edition language="English">FairyTale</edition>
</editions>
</project>
</projects>
</Book>
"@
$xml.SelectNodes("/Book/projects/editions")
}
f3
I wish to select "language=English", with content either contains "Novel" or equals "FairyTale", so my expected output is:
Novel_1
Novel_2
FairyTale
So how can I change my "SelectNodes" statement? Thanks a lot!
Upvotes: 3
Views: 6580
Reputation: 89305
In xpath, you can combine multiple boolean values using standard boolean operators like or
and and
:
/Book/*/*/*/edition[@language='English' and (.='FairyTale' or contains(.,'Novel'))]
alternatively, separating and
operands into two predicates ([]
) :
/Book/*/*/*/edition[@language='English'][.='FairyTale' or contains(.,'Novel')]
For this case, you may also want to consider using starts-with()
function instead of contains()
to be more precise.
side note : *
is just my way to shorten the xpath expression to fit in one line without having to reduce efficeincy (f.e using //
axis like /Book//edition
), you are fine to use the actual element names in place of *
.
Upvotes: 3
Reputation: 13179
The solution below updates the xpath to the editions element, then applies the where to filter as you requested.
$xml.SelectNodes("/Book/projects/project/editions/edition") `
| Where-Object { $_.language -eq "English" } `
| Where-Object { $_."#text" -like "*novel*" -or $_."#text" -eq "FairyTale" } `
| Format-Table @{Expression={$_."#text"};Label="Novel"}
Upvotes: 2