通过添加Xelements的Xdoc decendends迭代

时间:2014-05-22 09:22:13

标签: c# linq file-io linq-to-xml xelement

我正在尝试制作一个项目经理程序,以帮助整理我的项目文件。它使用Xdocs来存储项目信息。

我的问题是,现在我希望包含一个更结构化的视图来查看与项目相关的文件。完成后应该看起来像这样(文件的一部分xml)

<files count="0">
  <folder foldername="Doks">
    <folder foldername="moks">
      <folder foldername="Floks">
        <doc>
          <fileType>doc</fileType>
          <filePath>G:\Doks\moks\Floks</filePath>
          <fileName>Dok1.doc</fileName>
          <fileID>0</fileID>
        </doc>
      </folder>
    </folder>
    <folder foldername="goks">
      <folder foldername="Floks">
        <doc>
          <fileType>doc</fileType>
          <filePath>G:\Doks\moks\Floks</filePath>
          <fileName>Dok1.doc</fileName>
          <fileID>0</fileID>
        </doc>
      </folder>
    </folder>
  </folder>
</files>

正如你所看到的那样,主文件夹是doks,它有两个包含子文件夹和文件的文件夹,当然它都是为测试创建的。

到目前为止,我的代码可以找到已存在的路径,但无法添加缺少的最后一部分。

这样做的原因是我认为XML与现实相似,而且我已经将GUI作为系统的一部分,它就像一个魅力。它也很容易阅读

这是代码。

// Folder is contains the path the file e.i.
//      <folder foldername="Doks">
//        <folder foldername="moks">
//          <folder foldername="Floks"/>
//          </folder>
//      </folder>
// the file han the info about that 
// the xdoc to insert/anex the file and folder too is FilesInProject that is a public xdocument property 

private void AnexFileinXdoc(XElement file, XElement folder)
    {
        // is there  even a folde to consider
        if (folder != null)
        {
            // folder desendens list, used by looping through it  to se how menny of the folder already exists
            XElement[] list = new XElement[1];
            // handle for only on folder
            if (folder.Elements().Count() > 0)
            {
                list = folder.DescendantsAndSelf().ToArray();
            }
            else
            {
                list[0] = folder;
            }
            // debug info ignore
            // XElement[] test = FilesInProject.Root.DescendantsAndSelf("folder").ToArray();
            // list of the folderes already found this was to insure that when the loop resets and checks for the nex folder i will not flag the previous as not created.. 
            List<XElement> foundFolders = new List<XElement>();
            for (int i = 0; i < list.Length; i++)
            {
                if (FilesInProject.Root.Elements().Count() > 0)
                {
                    foreach (XElement xelem in FilesInProject.Root.Elements("folder"))
                    {
                        if (xelem.FirstAttribute.Value == list[i].FirstAttribute.Value)
                        {
                            foundFolders.Add(xelem);
                            break;
                        }
                        else
                        {
                            if (!foundFolders.Contains(xelem))
                            {
                                list[i].DescendantsAndSelf().Last().Add(file);
                                xelem.Add(list[i]);// <-- here is the problem
                            }
                            else if (i == list.Length-1)
                            {
                               xelem.Add(file); //<-- here is the problem 
                            }
                        }
                    }
                 }
            }
        }
        else
        {
            FilesInProject.Root.Add(file); 
        }
    }

我的期望是: 当我通过死者预先找到将我的文件夹结构添加到xelement时,如果我发现它,我可以调用add on the element(xelem)并且FilesinProject xdoc会更新,遗憾的是它不会这样做而且我没有在这个问题上找不到任何东西。

我需要一种快速而简单的方法将两个结构合并在一起,所以我没有得到任何重复

1 个答案:

答案 0 :(得分:0)

找到解决方案并认为我应该在这里分享

在Else区块

    if (!foundFolders.Contains(xelem))
    {
       list[i].DescendantsAndSelf().Last().Add(file);
       xelem.Add(list[i]);// <-- here is the problem
    }
    else if (i == list.Length-1)
    {
       xelem.Add(file); //<-- here is the problem 
    }

我所要做的就是将xelem.Add()更改为像这样的查询

if (!foundFolders.Contains(xelem))
{
    list[i].DescendantsAndSelf().Last().Add(file);
    FilesInProject.Descendants("folder")
       .Where(item => item.Attribute("foldername").Value == xelem.FirstAttribute.Value).FirstOrDefault()
       .Add(list[i]);
}
else if (i == list.Length-1)
{
    FilesInProject.Descendants("folder")
       .Where(item => item.Attribute("foldername").Value == xelem.FirstAttribute.Value).FirstOrDefault()
       .Add(file);
}

它完美地工作:)

希望它也有助于其他人