Каков наилучший способ преобразования Html-таблицы в datatable

#c#-3.0

#c #-3.0

Вопрос:

У меня есть HTML-таблица.Я хочу преобразовать это в datatable. Каков наилучший способ сделать это? Спасибо

Ответ №1:

Не разбирайте HTML самостоятельно, существуют библиотеки синтаксического анализа, которые могут сделать это за вас. В сочетании с HTML Agility Pack и LINQ вы можете быстро справиться с этим.

 var doc = new HtmlDocument();
doc.Load(url);

var nodes = doc.DocumentNode.SelectNodes("//table/tr");
var table = new DataTable("MyTable");

var headers = nodes[0]
    .Elements("th")
    .Select(th => th.InnerText.Trim());
foreach (var header in headers)
{
    table.Columns.Add(header);
}

var rows = nodes.Skip(1).Select(tr => tr
    .Elements("td")
    .Select(td => td.InnerText.Trim())
    .ToArray());
foreach (var row in rows)
{
    table.Rows.Add(row);
}
  

Комментарии:

1. Позаботится ли это о colspans и стилизации таблиц (css)? Похоже, что это просто переведет разметку данных и элементов

2. @user327999: нет, это просто взаимно однозначное сопоставление. В DataTables все равно нет такой вещи, AFAIK.

3. Я только что скачал HtmlAgilityPack 1.4.6 для того, чтобы сделать это. На веб-сайте говорится, что документации пока нет. Я попытался последовать приведенному здесь примеру, но получил исключение NullReferenceException при этом: var headers = nodes[0].Elements("th").Select(th => th.InnerText.Trim()); Узлы были null . Как мне использовать этот элемент управления? Где я могу найти текущую документацию по этому вопросу?

4. @jp2code: Это будет зависеть от разметки, которую вы анализируете. Документации, по общему признанию, не хватает, но большинство методов имеют обычную XML-документацию, которой, насколько я проверял в последний раз, должно быть достаточно. Но я полагаю, что это было смоделировано по XmlDocument и связанным классам, поэтому, если вы знакомы с синтаксическим анализом XML с использованием библиотеки XML, вы должны чувствовать себя как дома. nodes это результат вызова HtmlNode.SelectNodes() , который вы передаете в селекторе xpath. По-видимому, в вашем примере не было найдено таблиц с непосредственными строками.

5. Я внес некоторые небольшие коррективы, чтобы они соответствовали моему столу, но все сработало отлично .. Большое вам спасибо.

Ответ №2:

…несколько лет спустя…

 var nodes = doc.DocumentNode.SelectNodes("//table/tr");
  

строка содержит опечатку и должна быть с двойной косой чертой после слова «таблица», и все работает как по маслу

 var nodes = doc.DocumentNode.SelectNodes("//table//tr");
  

Комментарии:

1. Это не обязательно правильно, по крайней мере, было бы неправильно классифицировать это как опечатку … и, в зависимости от ситуации, вероятно, неправильно. Большинство людей пишут таблицы, tr элементы которых являются прямыми дочерними элементами table узла. ( <table><tr>...</tr></table> ) Но подобное изменение могло бы потребоваться, если бы строки находились под tbody элементом. Было бы правильно, если бы это было так, но я бы сказал, что это не так часто. Но это вызовет проблемы, особенно когда задействованы вложенные таблицы. Но … это чисто ситуативно … как и в данном случае.