# Get XML elements with a particular attribute value

I have the following code to find xml elements that have a particular attribute value:

IEnumerable<XElement> elems =
xmlDoc.Descendants("elemName")
.Where(x =>
x.Attribute("attrName").Value
.Equals(
filename,
StringComparison.OrdinalIgnoreCase
)
);


The problem is that if the element does not have that attribute, according to the docs, it will return null and we'll get a crash when we try to do null.Value.

I've rewritten it like this:

IEnumerable<XElement> elems =
xmlDoc.Descendants("elemName")
.Where(x =>
((x.Attribute("attrName") == null)
? ""
: x.Attribute("attrName").Value).Equals(
filename,
StringComparison.OrdinalIgnoreCase
)
);


But I think it's a bit ugly. Is there an idiomatic way of doing this - I imagine this is a fairly common operation? I suppose I could just do a regular loop.

I think you could use the null-conditional operator for x.Attribute("attrName").Value and swap arguments of String.Equals to avoid the NullReferenceException as follows:

IEnumerable<XElement> elems =
xmlDoc.Descendants("elemName")
.Where(x =>
filename.Equals(
x.Attribute("attrName")?.Value,
StringComparison.OrdinalIgnoreCase
)
);


There is a trick - you can cast XAttribute to some data types: string, int, long, Guid, DateTime, bool etc and their nullable brothers. And if type supports null value there will be no NullReferenceException. You will simply get null as result:

(string)x.Attribute("attrName")


Next: I suggest you to use more meaningful names for variables, even if it's one-letter variable. I.e. instead of x for element you can use e.

And last, you can write following extension method to nicely compare strings

public static bool EqualsIgnoreCase(this string s, string value)
{
return String.Equals(s, value, StringComparison.OrdinalIgnoreCase);
}


And finally your parsing query will look like

from e in xmlDoc.Descendants("elemName")
where filename.EqualsIgnoreCase((string)e.Attribute("attrName"))
select e;