制作一个简单的 xml 文件修改程序有困难吗?
Having trouble making a simple xml file modification program?
我有一些 XML 文件可以在结构中包含一些节点 <funding-source><institution-wrap>...</institution-wrap></funding-source>
我想获取节点内的值(如果有的话)并将这些值与另一个 XML 文件匹配,即 funding_info.xml 的节点 <skos>
如果匹配,则取其父节点的属性值 <skd>
然后
将 XML 主文件的 <funding-source><institution-wrap>...</institution-wrap></funding-source>
替换为 <funding-source><institution-wrap>...</institution-wrap><fundref-id>The attribute value found</fundref-id></funding-source>
。
funding_info.xml 如下所示
<?xml version="1.0" encoding="UTF-8"?>
<item>
<skd id="inst/10.1.3169">
<skosl>
<skos>NSF</skos>
</skosl>
<skosl>
<skos>National Science Foundation</skos>
</skosl>
<skosl>
<skos>Jatio Bigyan Songothon</skos>
</skosl>
</skd>
<skd id="inst/10.1.4560">
<skosl>
<skos>Massachusetts Institute of Technology</skos>
</skosl>
<skosl>
<skos>MIT</skos>
</skosl>
<skosl>
<skos>Massachusetts Institute of Technology, USA</skos>
</skosl>
</skd>
<skd id="inst/11.2.30213">
<skosl>
<skos>European Union</skos>
</skosl>
<skosl>
<skos>European Union</skos>
</skosl>
<skosl>
<skos>European Union FP7 Programme</skos>
</skosl>
</skd>
</item>
例如,如果我要修改的 XML 文件包含一些节点,例如
<funding-source><institution-wrap>NSF</institution-wrap></funding-source>
<funding-source><institution-wrap>Caltech</institution-wrap></funding-source>
<funding-source><institution-wrap>Massachusetts Institute of Technology, USA</institution-wrap></funding-source>
输出应该是
<funding-source><institution-wrap>NSF</institution-wrap><fundref-id>10.1.3169</fundref-id></funding-source>
<funding-source><institution-wrap>Caltech</institution-wrap></funding-source>
<funding-source><institution-wrap>Massachusetts Institute of Technology, USA</institution-wrap><fundref-id>10.1.4560</fundref-id></funding-source>
由于在 funding_info.xml 的任何 <skos>
节点中都找不到加州理工学院,因此其值未更改。
我不确定如何解决这个问题,但下面是我尝试过但中途卡住的方法
static void Main(string[] args)
{
XDocument doc = XDocument.Load(@"C:\Users\Desktop\my_sample.xml", LoadOptions.PreserveWhitespace);
var x = doc.Descendants("funding-source").Elements("institution-wrap").Select(a => a.Value).ToArray();
if (x.Any())
{
foreach (var cont in x)
{
XDocument doc2 = XDocument.Load(@"C:\Users\Desktop\funding_info.xml",
LoadOptions.PreserveWhitespace);
var y = doc2.Descendants("skos").Ancestors("skosl").Ancestors("skd").Attributes("id")
.Select(a => a.Value);
if (doc2.Descendants("skos").Any().Value(cont))
{
var y = doc2.Descendants("skos").Ancestors("skosl").Ancestors("skd").Attributes("id")
.Select(a => a.Value).First();
............. ...................
............. ..................
}
}
}
Console.ReadLine();
}
读入您的 funding_info.xml 文件并创建机构名称和 skd id 之间的映射。然后,您可以查看所有资金来源元素并检查它们是否已经具有 ID。如果不是,请查看该映射以查看它是否具有已知值。如果是,请添加 id。
var fundingDoc = XDocument.Load(pathToFundingInfo);
// creating a lookup since there are multiple instances of the institutions
var skdIds = fundingDoc.Descendants("skd").Elements("skosl")
.ToLookup(s => (string)s.Element("skos"), s => (string)s.Parent.Attribute("id"));
var outDoc = XDocument.Load(pathToUpdatedFile);
foreach (var f in outDoc.Descendants("funding-source"))
{
if (f.Element("fundref-id") == null)
{
var name = (string)f.Element("institution-wrap");
var skd = skdIds[name].FirstOrDefault(); // just take the first one
if (skd != null)
f.Add(new XElement("fundref-id", skd.Substring("inst/".Length)));
}
}
outDoc.Save(pathToUpdatedFile);
这应该产生如下输出:
<root>
<funding-source>
<institution-wrap>NSF</institution-wrap>
<fundref-id>10.1.3169</fundref-id>
</funding-source>
<funding-source>
<institution-wrap>Caltech</institution-wrap>
</funding-source>
<funding-source>
<institution-wrap>Massachusetts Institute of Technology, USA</institution-wrap>
<fundref-id>10.1.4560</fundref-id>
</funding-source>
</root>
如果您想使其不区分大小写,请将查找的键全部设为大写或小写。
// ...
var skdIds = fundingDoc.Descendants("skd").Elements("skosl")
.ToLookup(s => s.Element("skos").Value.ToUpperInvariant(), s => (string)s.Parent.Attribute("id"));
// ...
var name = f.Element("institution-wrap").Value.ToUpperInvariant();
// ...
我有一些 XML 文件可以在结构中包含一些节点 <funding-source><institution-wrap>...</institution-wrap></funding-source>
我想获取节点内的值(如果有的话)并将这些值与另一个 XML 文件匹配,即 funding_info.xml 的节点 <skos>
如果匹配,则取其父节点的属性值 <skd>
然后
将 XML 主文件的 <funding-source><institution-wrap>...</institution-wrap></funding-source>
替换为 <funding-source><institution-wrap>...</institution-wrap><fundref-id>The attribute value found</fundref-id></funding-source>
。
funding_info.xml 如下所示
<?xml version="1.0" encoding="UTF-8"?>
<item>
<skd id="inst/10.1.3169">
<skosl>
<skos>NSF</skos>
</skosl>
<skosl>
<skos>National Science Foundation</skos>
</skosl>
<skosl>
<skos>Jatio Bigyan Songothon</skos>
</skosl>
</skd>
<skd id="inst/10.1.4560">
<skosl>
<skos>Massachusetts Institute of Technology</skos>
</skosl>
<skosl>
<skos>MIT</skos>
</skosl>
<skosl>
<skos>Massachusetts Institute of Technology, USA</skos>
</skosl>
</skd>
<skd id="inst/11.2.30213">
<skosl>
<skos>European Union</skos>
</skosl>
<skosl>
<skos>European Union</skos>
</skosl>
<skosl>
<skos>European Union FP7 Programme</skos>
</skosl>
</skd>
</item>
例如,如果我要修改的 XML 文件包含一些节点,例如
<funding-source><institution-wrap>NSF</institution-wrap></funding-source>
<funding-source><institution-wrap>Caltech</institution-wrap></funding-source>
<funding-source><institution-wrap>Massachusetts Institute of Technology, USA</institution-wrap></funding-source>
输出应该是
<funding-source><institution-wrap>NSF</institution-wrap><fundref-id>10.1.3169</fundref-id></funding-source>
<funding-source><institution-wrap>Caltech</institution-wrap></funding-source>
<funding-source><institution-wrap>Massachusetts Institute of Technology, USA</institution-wrap><fundref-id>10.1.4560</fundref-id></funding-source>
由于在 funding_info.xml 的任何 <skos>
节点中都找不到加州理工学院,因此其值未更改。
我不确定如何解决这个问题,但下面是我尝试过但中途卡住的方法
static void Main(string[] args)
{
XDocument doc = XDocument.Load(@"C:\Users\Desktop\my_sample.xml", LoadOptions.PreserveWhitespace);
var x = doc.Descendants("funding-source").Elements("institution-wrap").Select(a => a.Value).ToArray();
if (x.Any())
{
foreach (var cont in x)
{
XDocument doc2 = XDocument.Load(@"C:\Users\Desktop\funding_info.xml",
LoadOptions.PreserveWhitespace);
var y = doc2.Descendants("skos").Ancestors("skosl").Ancestors("skd").Attributes("id")
.Select(a => a.Value);
if (doc2.Descendants("skos").Any().Value(cont))
{
var y = doc2.Descendants("skos").Ancestors("skosl").Ancestors("skd").Attributes("id")
.Select(a => a.Value).First();
............. ...................
............. ..................
}
}
}
Console.ReadLine();
}
读入您的 funding_info.xml 文件并创建机构名称和 skd id 之间的映射。然后,您可以查看所有资金来源元素并检查它们是否已经具有 ID。如果不是,请查看该映射以查看它是否具有已知值。如果是,请添加 id。
var fundingDoc = XDocument.Load(pathToFundingInfo);
// creating a lookup since there are multiple instances of the institutions
var skdIds = fundingDoc.Descendants("skd").Elements("skosl")
.ToLookup(s => (string)s.Element("skos"), s => (string)s.Parent.Attribute("id"));
var outDoc = XDocument.Load(pathToUpdatedFile);
foreach (var f in outDoc.Descendants("funding-source"))
{
if (f.Element("fundref-id") == null)
{
var name = (string)f.Element("institution-wrap");
var skd = skdIds[name].FirstOrDefault(); // just take the first one
if (skd != null)
f.Add(new XElement("fundref-id", skd.Substring("inst/".Length)));
}
}
outDoc.Save(pathToUpdatedFile);
这应该产生如下输出:
<root>
<funding-source>
<institution-wrap>NSF</institution-wrap>
<fundref-id>10.1.3169</fundref-id>
</funding-source>
<funding-source>
<institution-wrap>Caltech</institution-wrap>
</funding-source>
<funding-source>
<institution-wrap>Massachusetts Institute of Technology, USA</institution-wrap>
<fundref-id>10.1.4560</fundref-id>
</funding-source>
</root>
如果您想使其不区分大小写,请将查找的键全部设为大写或小写。
// ...
var skdIds = fundingDoc.Descendants("skd").Elements("skosl")
.ToLookup(s => s.Element("skos").Value.ToUpperInvariant(), s => (string)s.Parent.Attribute("id"));
// ...
var name = f.Element("institution-wrap").Value.ToUpperInvariant();
// ...