【发布时间】:2017-01-29 02:28:30
【问题描述】:
已解决 长话短说,不要在 XSL 转换中使用 CDATA。请继续阅读以了解详细信息。
背景 标准 C# 应用程序使用 XmlSerializer 将对象保存到 XML 文件。我需要获取保存的 XML 文件,添加对 XSL 转换的引用,应用所述转换,然后另存为 .graphml
问题 目前我的输出似乎有不正确的编码。 符号表示为“<”和“>”,这不是有效的 graphml(或 xml)
详情 以下是当前输出文件的样子:
<?xml version="1.0" encoding="utf-8"?>
<graphml xmlns="http://graphml.graphdrawing.org/xmlns"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://graphml.graphdrawing.org/xmlns
http://graphml.graphdrawing.org/xmlns/1.0/graphml.xsd">
<graph id="G" edgedefault="undirected">
<node id="n1"/>
<edge source="n1" target="n2"/>
<edge source="n1" target="n3"/>
<edge source="n1" target="n5"/>
<edge source="n1" target="n7"/>
<edge source="n1" target="n9"/>
<node id="n2"/>
<edge source="n2" target="n1"/>
<edge source="n2" target="n9"/>
对于它的价值,我知道我正在转换的 XML 是有效的(并且格式正确),并且我知道 xsl 文件是有效的并且可以正常工作,因为我可以在其他文件上使用它就好了. C# 应用 XSL 转换的方式导致了这个问题。 以下是相关代码:
// Create an XML writer
XmlSerializer writer = new XmlSerializer(typeof(formattedMeshNet));
var path = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments) + "\\netTransform.xml";
var transformPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments) + "\\GraphFormatTransform.xsl";
var savePath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments) + "\\ExportedNetwork.graphml";
System.IO.FileStream file = System.IO.File.Create(path);
writer.Serialize(file, saveMe);
file.Close();
// Add style sheet association
XmlDocument xDoc = new XmlDocument();
var transformAssn = xDoc.CreateProcessingInstruction("xml-stylesheet", "type=\"text/xsl\" href=\"GraphFormatTransform.xsl\"");
xDoc.AppendChild(transformAssn);
// Load xml just saved
System.Xml.Xsl.XslCompiledTransform myXslTransform;
myXslTransform = new System.Xml.Xsl.XslCompiledTransform();
myXslTransform.Load(transformPath);
myXslTransform.Transform(path, savePath);
任何想法将不胜感激!如果您发现我遗漏了任何内容,请随时询问详细信息:)
可能相关的问题并没有真正告诉我任何事情,但您可能会得到一些有用的信息: XSL transformation give me wrong encoding
我也尝试过这里的建议: The XslCompiledTransform output encoding
谢谢!
** 编辑 **
根据请求,这里是完整的 XML 文档和相关的 XSL 转换
<?xml version="1.0"?>
<formattedMeshNet xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<contents>
<node>
<nodeID>1</nodeID>
<physNeighbors>
<int>4</int>
<int>6</int>
<int>7</int>
<int>8</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>2</nodeID>
<physNeighbors>
<int>4</int>
<int>11</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>3</nodeID>
<physNeighbors>
<int>4</int>
<int>9</int>
<int>10</int>
<int>11</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>4</nodeID>
<physNeighbors>
<int>1</int>
<int>2</int>
<int>3</int>
<int>8</int>
<int>11</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>5</nodeID>
<physNeighbors>
<int>8</int>
<int>11</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>6</nodeID>
<physNeighbors>
<int>1</int>
<int>7</int>
<int>8</int>
<int>10</int>
<int>12</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>7</nodeID>
<physNeighbors>
<int>1</int>
<int>6</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>8</nodeID>
<physNeighbors>
<int>1</int>
<int>4</int>
<int>5</int>
<int>6</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>9</nodeID>
<physNeighbors>
<int>3</int>
<int>11</int>
<int>12</int>
<int>13</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>10</nodeID>
<physNeighbors>
<int>3</int>
<int>6</int>
<int>13</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>11</nodeID>
<physNeighbors>
<int>2</int>
<int>3</int>
<int>4</int>
<int>5</int>
<int>9</int>
<int>13</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>12</nodeID>
<physNeighbors>
<int>6</int>
<int>9</int>
</physNeighbors>
<visited />
<neighbors />
</node>
<node>
<nodeID>13</nodeID>
<physNeighbors>
<int>9</int>
<int>10</int>
<int>11</int>
</physNeighbors>
<visited />
<neighbors />
</node>
</contents>
</formattedMeshNet>
XSL
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:template match="/">
<![CDATA[
<graphml xmlns="http://graphml.graphdrawing.org/xmlns"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://graphml.graphdrawing.org/xmlns
http://graphml.graphdrawing.org/xmlns/1.0/graphml.xsd">]]>
<![CDATA[<graph id="G" edgedefault="undirected">]]>
<xsl:for-each select="/formattedMeshNet/contents/node">
<xsl:variable name="parentNodeID">
<xsl:value-of select="nodeID" />
</xsl:variable>
<![CDATA[<node id="n]]><xsl:copy-of select="$parentNodeID" /><![CDATA["/>]]>
<xsl:for-each select="physNeighbors/int">
<![CDATA[<edge source="n]]><xsl:copy-of select="$parentNodeID" /><![CDATA[" target="n]]><xsl:value-of select="." /><![CDATA["/>]]>
</xsl:for-each>
</xsl:for-each>
<![CDATA[</graph>
</graphml>]]>
</xsl:template>
</xsl:stylesheet>
【问题讨论】:
-
除了注释
// Add style sheet association之后的三行似乎没有使用和创建在其余代码中使用的任何对象外,我在 C# 中没有看到任何错误。但是XslCompiledTransformLoad和Transform的使用无论如何都没有关系,似乎没问题。所以我们需要查看最少的 XML 输入和 XSLT 样式表来判断问题所在。 -
@Martin_Honnen 我已经添加了 XML 和 XSLT 样式表
-
您正在使用 CDATA,所以这是预期的输出。
-
@michael.hor257k 需要 CDATA 以防止我插入的标签干扰 XSL。不过,我敢打赌,您一定会有所收获,因此,如果您愿意解释如何绕过它,那将很有用。
-
恐怕我无法解释,因为我不知道您要在这里完成什么。而且我不明白您所说的“保持插入的标签不会干扰 XSL”是什么意思。我刚刚运行了您的代码并收到了与您报告的结果相同的结果。我很确定如果你希望你的结果是 XML(就像 GraphML 应该是),那么你不应该(也不需要)在你的样式表中使用 CDATA。