كيفية استخراج علامة التعريف من XML / HTML باستخدام LinQ؟

StackOverflow https://stackoverflow.com/questions/1313529

  •  19-09-2019
  •  | 
  •  

سؤال

أحاول تحليل بعض البيانات من ملف HTML، لكن عبارة LinQ الخاصة بي لا يعمل. هنا هو XML / HTML. أدناه، كيف يمكنني استخراج السلسلة "41.8؛ 12.23" من علامة التجزية GEO.Position؟ شكرا!!

هنا هو بلدي لينك

   String longLat = (String)
        from el in xdoc.Descendants()
              where
               (string)el.Name.LocalName == "meta"
               & el.FirstAttribute.Name == "geo.position"
                select (String) el.LastAttribute.Value;

هنا هو بلدي Xdocument

<span>
  <!--CTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
        "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dt -->
  <html xmlns="http://www.w3.org/1999/xhtml">
    <head>
      <meta content="application/xhtml+xml; charset=utf-8" http-equiv="Content-Type" />
      <meta content="text/css" http-equiv="Content-Style-Type" />
      <meta name="geo.position" content="41.8;12.23" />
      <meta name="geo.placename" content="RomeFiumicino, Italy" />
      <title>RomeFiumicino, Italy</title>
    </head>
    <body />
  </html>
</span>

تحرير: استعلمني كما هو معطى إرجاع لا شيء. يبدو أن الاستعلام "الداخلي" إرجاع قائمة بجميع عناصر التعريف بدلا من عنصر واحد فقط أريده.

تحرير: يعمل استعلام LINQ التالي على نفس XDocument لإعادة التثبيت على جدول اسم الفئة = "البيانات"

    var dataTable =
        from el in xdoc.Descendants()
        where (string)el.Attribute("class") == "data"
        select el;
هل كانت مفيدة؟

المحلول

أ span حولك html بطاقة شعار؟

يمكنك القيام بذلك مع xlinq، لكنه سيدعم فقط XML بشكل جيد. قد ترغب في إلقاء نظرة على حزمة أجريتي HTML في حين أن.

يحرر - هذا يعمل بالنسبة لي:

string xml = "...";
var geoPosition = XElement.Parse(xml).Descendants().
    Where(e => e.Name.LocalName == "meta" &&
        e.Attribute("name") != null &&
        e.Attribute("name").Value == "geo.position").
    Select(e => e.Attribute("content").Value).
    SingleOrDefault();

نصائح أخرى

أراهن أن المشكلة التي تواجهها تأتي من عدم الرجوع إلى مساحة الاسم بشكل صحيح مع XmlNamespaceManager. وبعد فيما يلي طريقتان للقيام بذلك:

string xml =
        @"<span>
   <!--CTYPE html PUBLIC ""-//W3C//DTD XHTML 1.0 Transitional//EN""
        ""http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dt -->
   <html xmlns=""http://www.w3.org/1999/xhtml"">
    <head>
     <meta content=""application/xhtml+xml; charset=utf-8"" http-equiv=""Content-Type"" />
      <meta content=""text/css"" http-equiv=""Content-Style-Type"" />
      <meta name=""geo.position"" content=""41.8;12.23"" />
      <meta name=""geo.placename"" content=""RomeFiumicino, Italy"" />
      <title>RomeFiumicino, Italy</title>
    </head>
    <body />
   </html>
    </span>";

    string ns = "http://www.w3.org/1999/xhtml";
    XmlNamespaceManager nsm;

    // pre-Linq:
    XmlDocument d = new XmlDocument();
    d.LoadXml(xml);
    nsm = new XmlNamespaceManager(d.NameTable);
    nsm.AddNamespace("h", ns);

    Console.WriteLine(d.SelectSingleNode(
        "/span/h:html/h:head/h:meta[@name='geo.position']/@content", nsm).Value);

    // Linq - note that you have to create an XmlReader so that you can
    // use its NameTable in creating the XmlNamespaceManager:
    XmlReader xr = XmlReader.Create(new StringReader(xml));
    XDocument xd = XDocument.Load(xr);
    nsm = new XmlNamespaceManager(xr.NameTable);
    nsm.AddNamespace("h", ns);

    Console.WriteLine(
        xd.XPathSelectElement("/span/h:html/h:head/h:meta[@name='geo.position']", nsm)
            .Attribute("content").Value);

وأنا أتفق مع Thorarin - استخدم حزمة أجراس أتش تي أم أل، إنها أكثر قوة.

ومع ذلك، أظن أن المشكلة التي تواجهها Linqtoxml هي بسبب مساحة الاسم. يرى MSDN هنا لكيفية التعامل معها في استفساراتك.

"إذا كان لديك XML وهو في مساحة الاسم الافتراضية، فلا يزال يتعين عليك إعلان متغير Xnamespace، ودمجه بالاسم المحلي لإعداد اسم مؤهل لاستخدامه في الاستعلام.

واحدة من أكثر المشكلات شيوعا عند الاستعلام عن أشجار XML هي أنه إذا كانت شجرة XML تحتوي على مساحة اسم افتراضية، يكتب المطور أحيانا الاستعلام كما لو أن XML لم يكن في مساحة الاسم ".

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top