xml文件看起来像
<employees>
<employee id='1'>
<Profile_Name>admin</Profile_Name>
<UserName>user</UserName>
</employee>
<employee id='2'>
<Profile_Name>Admin</Profile_Name>
<UserName>USER</UserName>
</employee>
<employee id='3'>
<Profile_Name>Adminnn</Profile_Name>
<UserName>userrrr</UserName>
</employee>
这是我的xpath
employees/employee
[not(Deleted)]
[Profile_Name[last()]
[translate(.,
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
]
=
'admin'or
UserName[last()]
[translate(.,
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
]
=
'user'
]
它应该选择employee
不具有Deleted
子元素的元素和Profile_Name
= admin或UserName
= user,而不管profileName和UserName
它运作正常,但不考虑字符大小。
它应该返回employee
id
= 1和2
答案 0 :(得分:1)
你的翻译错误。代码生成的XPath表达式将测试类似
的内容Profile_Name[last()][translate(.,'ABCDE...', 'abcde...')] = 'foo'
即。它将找到最后一个Profile_Name
元素,检查该元素是否具有非空值,然后将该值(例如Foo
)与字符串foo
进行比较。相反,你需要
translate(Profile_Name[last()],'ABCDE...', 'abcde...') = 'foo'
对翻译的值而不是原始值进行比较。完整的表达式应该类似于
var xpath = "/employees/employee[not(Deleted)][translate(Profile_Name[last()],'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz')='" + ProfileName.ToLower() + "' or translate(UserName[last()],'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz')='" + UserName.ToLower() + "']";
答案 1 :(得分:1)
现在你有了这个(格式正确使其可读):
/employees/employee
[not(Deleted)]
[Profile_Name[last()]
[translate(Profile_Name[last()],
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
]
=
'admin'or
UserName[last()]
[translate(.,
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
]
=
'user'
]";
显然是错误的 - 包含translate()
的谓词过早关闭。
可能你想要这个:
/employees/employee
[not(Deleted)]
[translate(Profile_Name[last()],
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
=
'admin'
or
translate(UserName[last()],
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
=
'user'
]
基于XSLT的验证:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="/">
<xsl:copy-of select=
"/employees/employee
[not(Deleted)]
[translate(Profile_Name[last()],
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
=
'admin'
or
translate(UserName[last()],
'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
'abcdefghijklmnopqrstuvwxyz'
)
=
'user'
]"/>
</xsl:template>
</xsl:stylesheet>
将此转换应用于以下XML文档(基于提供的转换,但添加了更多employee
元素以提供更多必要的测试用例):
<employees>
<employee id='1'>
<Profile_Name>admin</Profile_Name>
<UserName>user</UserName>
</employee>
<employee id='2'>
<Profile_Name>Admin</Profile_Name>
<UserName>USER</UserName>
</employee>
<employee id='3'>
<Deleted/>
<Profile_Name>Admin</Profile_Name>
<UserName>user</UserName>
</employee>
<employee id='4'>
<Profile_Name>Adminnn</Profile_Name>
<UserName>userrrr</UserName>
</employee>
</employees>
评估Xpath表达式并将此评估结果复制到输出中:
<employee id="1">
<Profile_Name>admin</Profile_Name>
<UserName>user</UserName>
</employee>
<employee id="2">
<Profile_Name>Admin</Profile_Name>
<UserName>USER</UserName>
</employee>
答案 2 :(得分:0)
.NET XSLT实现允许在样式表中编写自定义托管函数。对于小写(),它可以是:
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt" xmlns:utils="urn:myExtension" exclude-result-prefixes="msxsl">
<xsl:output method="xml" indent="yes"/>
<msxsl:script implements-prefix="utils" language="C#">
<![CDATA[
public string ToLower(string stringValue)
{
string result = String.Empty;
if(!String.IsNullOrEmpty(stringValue))
{
result = stringValue.ToLower();
}
return result;
}
]]>
</msxsl:script>
<!-- using of our custom function -->
<lowercaseValue>
<xsl:value-of select="utils:ToLower($myParam)"/>
</lowercaseValue>
假设,这可能很慢,但仍然可以接受。
不要忘记启用嵌入式脚本支持转换:
// Create the XsltSettings object with script enabled.
XsltSettings xsltSettings = new XsltSettings(false, true);
XslCompiledTransform xslt = new XslCompiledTransform();
// Load stylesheet
xslt.Load(xsltPath, xsltSettings, new XmlUrlResolver());