#c# #xml #datagridview #linq-to-xml
#c# #xml #datagridview #linq-to-xml
Вопрос:
Я знаю, что есть много ресурсов, которые показывают, как привязывать DataGridViews к XML-файлам или заполнять из XML, но XML, который я использую в качестве источника, немного сложнее, чем любой пример, который я видел, и я испытываю трудности. (хотя это действительно не должно быть сложно)
По сути, мне нужно выполнить несколько запросов (я думаю), чтобы получить данные, которые я хочу заполнить в DGV, потому что элементы, из которых я хочу получить содержимое, находятся на разных родительских узлах XML.
Вот что у меня есть, и комментарии должны показать вам, чего я пытаюсь достичь:
XDocument xmlDoc = XDocument.Load("Techdocx_dml.xml");
var q = from c in xmlDoc.Root.Descendants("dmentry")
.Descendants("avee")
//.Descendants("dmtitle") I also need to access this descendant
select new
{
modelic = c.Element("modelic").Value,
sdc = c.Element("sdc").Value,
chapnum = c.Element("chapnum").Value,
section = c.Element("section").Value,
subsect = c.Element("subsect").Value,
subject = c.Element("subject").Value,
discode = c.Element("discode").Value,
discodev = c.Element("discodev").Value,
incode = c.Element("incode").Value,
incodev = c.Element("incodev").Value,
itemloc = c.Element("itemloc").Value,
// techname = c.Element("techname").Value,
//need this value, which is on the "dmtitle" node, not the "avee" node
};
dataGridView1.DataSource = q.ToList();
dataGridView1.ColumnHeadersVisible = false;
dataGridView1.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.AllCells;
Это то, что я хочу в моем DataGridView:
AA A 32 3 5 00 01 A 018 A A | Some title 1 | Introduction
AA A 32 3 5 00 01 A 920 A A | Some title 2 | Some infoname 2
Как мне этого добиться, пожалуйста? Пример XML ниже:
<dml xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<dmentry>
<addresdm>
<dmc>
<avee>
<modelic>AA</modelic>
<sdc>A</sdc>
<chapnum>32</chapnum>
<section>3</section>
<subsect>5</subsect>
<subject>00</subject>
<discode>01</discode>
<discodev>A</discodev>
<incode>018</incode>
<incodev>A</incodev>
<itemloc>A</itemloc>
</avee>
</dmc>
<dmtitle>
<techname>Some title 1</techname>
<infoname>Introduction</infoname>
</dmtitle>
<issno issno="001" type="New"/>
<issdate year="2016" month="06" day="10"/>
<language language="SX" country="GB"/>
</addresdm>
<security class="1"/>
</dmentry>
<dmentry>
<addresdm>
<dmc>
<avee>
<modelic>AA</modelic>
<sdc>A</sdc>
<chapnum>32</chapnum>
<section>3</section>
<subsect>5</subsect>
<subject>00</subject>
<discode>01</discode>
<discodev>A</discodev>
<incode>920</incode>
<incodev>A</incodev>
<itemloc>A</itemloc>
</avee>
</dmc>
<dmtitle>
<techname>Some title 2</techname>
<infoname>Some infoname 2</infoname>
</dmtitle>
<issno issno="001" type="New"/>
<issdate year="2016" month="06" day="10"/>
<language language="SX" country="GB"/>
</addresdm>
<security class="1"/>
</dmentry>
</dml>
Комментарии:
1. Не могли бы вы привести пример для вывода?
2. Я получаю именно то, что вы ожидаете от моего запроса. Я хочу то же самое, но с добавлением значений, показанных в запросе, который я закомментировал. Итак, значения всех дочерних элементов в теге <avee> (что я и получаю), а также значения двух дочерних элементов <dmtitle> .
3. вы можете создать таблицу данных со всеми нужными столбцами, а затем заполнить каждую строку двумя запросами linq. или просто создайте класс со всеми свойствами и назначьте эти свойства в двух запросах
Ответ №1:
Попробуйте это :
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Xml;
using System.Xml.Linq;
namespace WindowsFormsApplication11
{
public partial class Form1 : Form
{
const string FILENAME = @"c:temptest.xml";
public Form1()
{
InitializeComponent();
DataTable dt = new DataTable();
dt.Columns.Add("modelic", typeof(string));
dt.Columns.Add("sdc", typeof(string));
dt.Columns.Add("chapnum", typeof(string));
dt.Columns.Add("section", typeof(string));
dt.Columns.Add("subsect", typeof(string));
dt.Columns.Add("subject", typeof(string));
dt.Columns.Add("discode", typeof(string));
dt.Columns.Add("discodev", typeof(string));
dt.Columns.Add("incode", typeof(string));
dt.Columns.Add("incodev", typeof(string));
dt.Columns.Add("itemloc", typeof(string));
dt.Columns.Add("techname", typeof(string));
dt.Columns.Add("infoname", typeof(string));
XDocument doc = XDocument.Load(FILENAME);
foreach (XElement addresdm in doc.Descendants().Where(x => x.Name.LocalName == "addresdm"))
{
XElement avee = addresdm.Descendants("avee").FirstOrDefault();
XElement dmtitle = addresdm.Descendants("dmtitle").FirstOrDefault();
dt.Rows.Add(new object[] {
(string)avee.Element("modelic"),
(string)avee.Element("sdc"),
(string)avee.Element("chapnum"),
(string)avee.Element("section"),
(string)avee.Element("subsect"),
(string)avee.Element("subject"),
(string)avee.Element("discode"),
(string)avee.Element("discodev"),
(string)avee.Element("incode"),
(string)avee.Element("incodev"),
(string)avee.Element("itemloc"),
(string)dmtitle.Element("techname"),
(string)dmtitle.Element("infoname")
});
}
dataGridView1.DataSource = dt;
}
}
}
Комментарии:
1. Легенда. Большое вам спасибо!