LINQ to XMLでの行番号と行位置情報の取得について.
過去の内容は以下から見れます。よろしければご参照くださいませ。
今回は、IXmlLineInfoを利用して行番号と行位置の情報を取得する方法についてです.
IXmlLineInfoはXObjectにて明示的実装が行われているインターフェースです.
IXmlLineInfo型にキャストすることで、値を取得できるようになります.
尚、行番号などを取得する場合は、予め対象のXMLをロードする際に
LoadOptions.SetLineInfoを設定してロードしておく必要があります.
LoadOptions.SetLineInfoを設定せずにロードした状態で、IXmlLineInfoの情報を取得しても行番号は常に0となります.
以下、サンプルです。
namespace Gsf.Samples { using System; using System.Collections.Generic; using System.Linq; using System.Xml; using System.Xml.Linq; #region LinqSamples-87 /// <summary> /// LINQ to XMLのサンプルです. /// </summary> /// <remarks> /// IXmlLineInfoインターフェースから行番号を取得するサンプルです。 /// </remarks> public class LinqSamples87 : IExecutable { public void Execute() { // // IXmlLineInfo // IXmlLineInfoはXObjectにて明示的実装が行われているインターフェースである. // IXmlLineInfo型にキャストすることで、値を取得できるようになる。 // このインターフェースには以下のメソッドとプロパティが定義されている. // ■ HasLineInfoメソッド:行情報を持っているか否か. // ■ LineNumberプロパティ:行番号 // ■ LinePositionプロパティ:行位置 // // 尚、行番号などを取得する場合は、予め対象のXMLをロードする際に // LoadOptions.SetLineInfoを設定してロードしておく必要がある。 // LoadOptions.SetLineInfoを設定せずにロードした状態で、IXmlLineInfoの // 情報を取得しても行番号は常に0となる. // var root = BuildSampleXml(); foreach (var elem in root.Descendants()) { var info = elem as IXmlLineInfo; Console.WriteLine(elem.Name); Console.WriteLine("\tHasLineInfo == {0}", info.HasLineInfo()); Console.WriteLine("\tLineNumber == {0}", info.LineNumber); Console.WriteLine("\tLinePosition == {0}", info.LinePosition); } Console.WriteLine("========================================================="); // // 要素を追加. // var newElem = new XElement("NewElement", "NewElementValue"); root.Add(newElem); // // 再度行番号を表示. // 新規追加した要素からは行番号情報が取得出来ない. // foreach (var elem in root.Descendants()) { var info = elem as IXmlLineInfo; Console.WriteLine(elem.Name); Console.WriteLine("\tHasLineInfo == {0}", info.HasLineInfo()); Console.WriteLine("\tLineNumber == {0}", info.LineNumber); Console.WriteLine("\tLinePosition == {0}", info.LinePosition); } Console.WriteLine("========================================================="); } XElement BuildSampleXml() { // // サンプルXMLファイル // see: http://msdn.microsoft.com/ja-jp/library/vstudio/ms256479(v=vs.90).aspx // // 行番号を取得するためにLoadOptions.SetLineInfoを設定. return XElement.Load(@"xml/Books.xml", LoadOptions.SetLineInfo); } } #endregion }
実行すると以下のようになります。
Book HasLineInfo == True LineNumber == 3 LinePosition == 5 Author HasLineInfo == True LineNumber == 4 LinePosition == 8 Title HasLineInfo == True LineNumber == 5 LinePosition == 8 Genre HasLineInfo == True LineNumber == 6 LinePosition == 8 Price HasLineInfo == True LineNumber == 7 LinePosition == 8 PublishDate HasLineInfo == True LineNumber == 8 LinePosition == 8 Description HasLineInfo == True LineNumber == 9 LinePosition == 8 Book HasLineInfo == True LineNumber == 12 LinePosition == 5 Author HasLineInfo == True LineNumber == 13 LinePosition == 8 Title HasLineInfo == True LineNumber == 14 LinePosition == 8 Genre HasLineInfo == True LineNumber == 15 LinePosition == 8 Price HasLineInfo == True LineNumber == 16 LinePosition == 8 PublishDate HasLineInfo == True LineNumber == 17 LinePosition == 8 Description HasLineInfo == True LineNumber == 18 LinePosition == 8 ========================================================= Book HasLineInfo == True LineNumber == 3 LinePosition == 5 Author HasLineInfo == True LineNumber == 4 LinePosition == 8 Title HasLineInfo == True LineNumber == 5 LinePosition == 8 Genre HasLineInfo == True LineNumber == 6 LinePosition == 8 Price HasLineInfo == True LineNumber == 7 LinePosition == 8 PublishDate HasLineInfo == True LineNumber == 8 LinePosition == 8 Description HasLineInfo == True LineNumber == 9 LinePosition == 8 Book HasLineInfo == True LineNumber == 12 LinePosition == 5 Author HasLineInfo == True LineNumber == 13 LinePosition == 8 Title HasLineInfo == True LineNumber == 14 LinePosition == 8 Genre HasLineInfo == True LineNumber == 15 LinePosition == 8 Price HasLineInfo == True LineNumber == 16 LinePosition == 8 PublishDate HasLineInfo == True LineNumber == 17 LinePosition == 8 Description HasLineInfo == True LineNumber == 18 LinePosition == 8 NewElement HasLineInfo == False LineNumber == 0 LinePosition == 0 =========================================================
以下、参照リソースです。
- IXmlLineInfo インターフェイス
================================
過去の記事については、以下のページからご参照下さい。
- いろいろ備忘録日記まとめ
サンプルコードは、以下の場所で公開しています。
- いろいろ備忘録日記サンプルソース置き場