使用 grep 和正则表达式选择跨多行的文本
我正在尝试将行与仅包含 minOccurs 的 xs:element 标记相匹配。如下所示,其中一些在一行上包含两个搜索条件,其中一些跨越多行。有没有办法使用 grep 和正则表达式来选择它们。
<xs:element name="shipto">
<xs:complexType>
<xs:sequence>
<xs:element name="name" type="xs:string"/>
<xs:element name="address" type="xs:string"/>
<xs:element name="city" minOccurs="1" type="xs:string"/>
<xs:element name="country"
minOccurs="1" type="xs:string"/>
</xs:sequence>
</xs:complexType>
</xs:element>
正确的输出应该如下:
<xs:element name="city" minOccurs="1" type="xs:string"/>
<xs:element name="country"
minOccurs="1" type="xs:string"/>
I'm trying to match lines with the xs:element tag that only contain minOccurs. As seen below some of them contain both search criteria on one line, some of them span multiple lines. Is there a way of selecting them using grep and regular expressions.
<xs:element name="shipto">
<xs:complexType>
<xs:sequence>
<xs:element name="name" type="xs:string"/>
<xs:element name="address" type="xs:string"/>
<xs:element name="city" minOccurs="1" type="xs:string"/>
<xs:element name="country"
minOccurs="1" type="xs:string"/>
</xs:sequence>
</xs:complexType>
</xs:element>
The correct output should be as follows:
<xs:element name="city" minOccurs="1" type="xs:string"/>
<xs:element name="country"
minOccurs="1" type="xs:string"/>
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我建议不要使用正则表达式解析 XML。以稳健的方式将标签与结束标签匹配起来太复杂了。
Perl 中有一个使用 XML::XPath 的命令行工具“xpath”(Ubuntu 软件包 libxml-xpath-perl)。示例:
输出
I advise against parsing XML using regex. It is too complicated to match tags with end-tags in a robust way.
There is a command line tool "xpath" using XML::XPath in Perl (Ubuntu package libxml-xpath-perl). Example:
Output
假设格式良好的 XML(即没有未转义的 > 内部属性),那么您可能可以这样做:
但是,我不确定这是否适用于 grep,因为 grep 匹配单独的行,因此您可能需要编写一个 perl脚本或其他东西来做到这一点。
(请注意,如果您以某种方式拥有包含值
sminOccurs=
的属性,那么您需要变得更聪明,但由于这似乎是地址数据,我假设这不太可能,并且手动删除发生的任何情况都不会成为问题。)Assuming well-formed XML (i.e. no un-escaped > inside attributes) then you can probably do this:
However, I'm not sure this will work with grep, since grep matches individual lines, so you may need to write a perl script or something to do it.
(Note, if you somehow have attributes which contain the value
sminOccurs=
then you'd need to get cleverer, but since this appears to be address data, I'm assuming that's unlikely, and manually removing any that happen to occur isn't going to be a problem.)