Min*_*ing 12 .net c# xml linq-to-xml
我正在寻找一种可以有效地从XML中删除空标签的好方法.您有什么推荐的吗?正则表达式?的XDocument?XmlTextReader的?
例如,
const string original =
@"<?xml version=""1.0"" encoding=""utf-16""?>
<pet>
<cat>Tom</cat>
<pig />
<dog>Puppy</dog>
<snake></snake>
<elephant>
<africanElephant></africanElephant>
<asianElephant>Biggy</asianElephant>
</elephant>
<tiger>
<tigerWoods></tigerWoods>
<americanTiger></americanTiger>
</tiger>
</pet>";
Run Code Online (Sandbox Code Playgroud)
可能成为:
const string expected =
@"<?xml version=""1.0"" encoding=""utf-16""?>
<pet>
<cat>Tom</cat>
<dog>Puppy</dog>
<elephant>
<asianElephant>Biggy</asianElephant>
</elephant>
</pet>";
Run Code Online (Sandbox Code Playgroud)
Jam*_*iec 28
将原件加载到XDocument
并使用以下代码可以得到所需的输出:
var document = XDocument.Parse(original);
document.Descendants()
.Where(e => e.IsEmpty || String.IsNullOrWhiteSpace(e.Value))
.Remove();
Run Code Online (Sandbox Code Playgroud)
Dan*_*eld 16
这是对处理属性的已接受答案的改进:
XDocument xd = XDocument.Parse(original);
xd.Descendants()
.Where(e => (e.Attributes().All(a => a.IsNamespaceDeclaration || string.IsNullOrWhiteSpace(a.Value))
&& string.IsNullOrWhiteSpace(e.Value)
&& e.Descendants().SelectMany(c => c.Attributes()).All(ca => ca.IsNamespaceDeclaration || string.IsNullOrWhiteSpace(ca.Value))))
.Remove();
Run Code Online (Sandbox Code Playgroud)
这里的想法是在删除元素之前检查元素上的所有属性是否也为空.还有一种情况是空后代可以具有非空属性.我插入了第三个条件来检查该元素在其后代中是否具有所有空属性. 考虑以下添加了node8的文档:
<root>
<node />
<node2 blah='' adf='2'></node2>
<node3>
<child />
</node3>
<node4></node4>
<node5><![CDATA[asdfasdf]]></node5>
<node6 xmlns='urn://blah' d='a'/>
<node7 xmlns='urn://blah2' />
<node8>
<child2 d='a' />
</node8>
</root>
Run Code Online (Sandbox Code Playgroud)
这会变成:
<root>
<node2 blah="" adf="2"></node2>
<node5><![CDATA[asdfasdf]]></node5>
<node6 xmlns="urn://blah" d="a" />
<node8>
<child2 d='a' />
</node8>
</root>
Run Code Online (Sandbox Code Playgroud)
原来和改进这个问题的答案将失去node2
与node6
和node8
节点.检查e.IsEmpty
将工作,如果你只是想去掉节点等<node />
,但如果你要两者是redunant <node />
和<node></node>
.如果您还需要删除空属性,则可以执行以下操作:
xd.Descendants().Attributes().Where(a => string.IsNullOrWhiteSpace(a.Value)).Remove();
xd.Descendants()
.Where(e => (e.Attributes().All(a => a.IsNamespaceDeclaration))
&& string.IsNullOrWhiteSpace(e.Value))
.Remove();
Run Code Online (Sandbox Code Playgroud)
这会给你:
<root>
<node2 adf="2"></node2>
<node5><![CDATA[asdfasdf]]></node5>
<node6 xmlns="urn://blah" d="a" />
</root>
Run Code Online (Sandbox Code Playgroud)