LINQ 查询返回空结果

发布于 2024-12-09 18:40:57 字数 1151 浏览 0 评论 0原文

我有以下代码

nodes = data.Descendants(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Results")).Nodes();
        System.Collections.Generic.IEnumerable<Result> res = new List<Result>();
        if (nodes.Count() > 0)
        {
            var results = from uris in nodes
                          select new Result
        {
            URL =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Url")).Value,
            Title =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Title")).Value,
            Description =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Description")).Value,
            DateTime =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}DateTime")).Value,
        };
            res = results;
        }

,其中 Results 是定义了 URL、标题、描述和日期时间变量的对象。

这一切正常工作正常,但是当节点中的“节点”不包含描述元素(或者至少我认为这就是抛出它的原因)时,程序会点击“res = results;” 代码行并抛出“对象引用未设置为...”错误并突出显示“选择新结果”之后的整个部分。

我该如何解决此问题?

I have the following code

nodes = data.Descendants(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Results")).Nodes();
        System.Collections.Generic.IEnumerable<Result> res = new List<Result>();
        if (nodes.Count() > 0)
        {
            var results = from uris in nodes
                          select new Result
        {
            URL =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Url")).Value,
            Title =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Title")).Value,
            Description =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Description")).Value,
            DateTime =
((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}DateTime")).Value,
        };
            res = results;
        }

Where Results is a object who has those URL, Title, Description, and DateTime variables defined.

This all works fine normally, but when a 'node' in nodes doesnt contain a Description element (or at least I think thats whats throwing it) the program hits the "res = results;"
line of code and throws a 'object reference not set to...' error and highlights the whole section right after "select new Results"..

How do I fix this?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

演多会厌 2024-12-16 18:40:57

最简单的方法是转换为 string 而不是使用 Value 属性。这样,您最终会得到 Descriptionnull 引用。

然而,您的代码也可以变得更好:

XNamespace ns = "http://schemas.microsoft.com/LiveSearch/2008/04/XML/web";

var results = data.Descendants(ns + "Results")
                  .Elements()
                  .Select(x => new Result 
                          {
                            URL = (string) x.Element(ns + "Url"),
                            Title = (string) x.Element(ns + "Title"),
                            Description = (string) x.Element(ns + "Description"),
                            DateTime = (string) x.Element(ns + "DateTime")
                          })
                  .ToList();

看看这简单多了?使用的技术:

  • 在空序列上调用 ToList() 无论如何都会给你一个列表
  • ,这样你就只会执行一次查询;在调用 Count() 之前,这可能会遍历每个节点。一般来说,使用 Any() 而不是 Count() > 0) - 但这一次只是使列表无条件更简单。
  • 使用 Elements() 方法获取子元素,而不是多次转换。 (如果之前的代码遇到任何非元素节点,则会引发异常)
  • 使用从字符串到 XNamespace 的隐式转换
  • 使用 +(XNamespace, string) 运算符获取XName

The simplest way is to cast to string instead of using the Value property. That way you'll end up with a null reference for the Description instead.

However, your code can also be made a lot nicer:

XNamespace ns = "http://schemas.microsoft.com/LiveSearch/2008/04/XML/web";

var results = data.Descendants(ns + "Results")
                  .Elements()
                  .Select(x => new Result 
                          {
                            URL = (string) x.Element(ns + "Url"),
                            Title = (string) x.Element(ns + "Title"),
                            Description = (string) x.Element(ns + "Description"),
                            DateTime = (string) x.Element(ns + "DateTime")
                          })
                  .ToList();

See how much simpler that is? Techiques used:

  • Calling ToList() on an empty sequence gives you a list anyway
  • This way you'll only ever perform the query once; before you were calling Count() which would potentially have iterated over each node. In general, use Any() instead of Count() > 0) - but this time just making the list unconditional is simpler.
  • Use the Elements() method to get child elements, rather than casting multiple times. (Your previous code would have thrown an exception if it had encountered any non-element nodes)
  • Use the implicit conversion from string to XNamespace
  • Use the +(XNamespace, string) operator to get an XName
鸠书 2024-12-16 18:40:57

如果未包含 Description 元素,则应

((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Description"))

在使用 Value 之前测试它是否不为 null。试试这个代码:

var results = from uris in nodes let des = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Description"))
                      select new Result
    {
        URL = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Url")).Value,
        Title = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Title")).Value,
        Description = (des != null) ? des.Value : string.Empty,
        DateTime = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}DateTime")).Value,
    };

If the Description element is not included you should test if this

((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Description"))

is not null before using Value. Try this code:

var results = from uris in nodes let des = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Description"))
                      select new Result
    {
        URL = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Url")).Value,
        Title = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}Title")).Value,
        Description = (des != null) ? des.Value : string.Empty,
        DateTime = ((XElement)uris).Element(XName.Get("{http://schemas.microsoft.com/LiveSearch/2008/04/XML/web}DateTime")).Value,
    };
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文