Подтвердить что ты не робот

LINQ to SQL и Null, как использовать Contains?

Вот запрос

from a in this._addresses
where a.Street.Contains(street) || a.StreetAdditional.Contains(streetAdditional)
select a).ToList<Address>()

если оба свойства в предложении where имеют значения, это работает нормально, но если, например, a.StreetAdditional является нулевым (в большинстве случаев), я получаю исключение с нулевой ссылкой.

Есть ли работа вокруг этого?

Спасибо,

4b9b3361

Ответ 1

Самый очевидный:

from a in this._addresses
where (a.Street != null && a.Street.Contains(street)) || (a.StreetAdditional != null && a.StreetAdditional.Contains(streetAdditional))
select a).ToList<Address>()

В качестве альтернативы вы можете написать метод расширения для Contains, который принимает пустой аргумент без ошибок. Некоторые могут сказать, что такой метод не так хорош, потому что он выглядит как обычный вызов метода, но допускается для нулевых значений (тем самым исключая обычные методы проверки нулевой точки).

Ответ 2

Я бы использовал оператор с нулевым коалесцированием...

(from a in this._addresses
where (a.Street ?? "").Contains(street) || (a.StreetAdditional ?? "").Contains(streetAdditional)
select a).ToList<Address>()

Ответ 3

Я бы создал метод расширения, чтобы возвращать пустую последовательность, если null, а затем вызов содержит метод.

public static IEnumerable<T> EmptyIfNull<T>(this IEnumerable<T> pSeq)
{
      return pSeq ?? Enumerable.Empty<T>();
}

from a in this._addresses
where a.Street.Contains(street) || 
      a.StreetAdditional.EmptyIfNull().Contains(streetAdditional)
select a).ToList<Address>()

Ответ 4

Сначала вы должны проверить, если StreetAdditional - null.

Try

where a.Street.Contains(street) || ((a != null) && a.StreetAdditional.Contains(streetAdditional))

Это работает, потому что && - это shortcut-operator, и если a != null дает false, второе выражение с null -значением не будет оцениваться, так как результат будет false в любом случае.

Ответ 5

Я не думаю, что SqlServer дал вам нулевое исключение. Если это так, то этот код явно не работает, хотя LinqToSql (как вы отметили вопрос).

string.Contains будет переведен в sql like, который не имеет никаких проблем с нулевыми значениями.

Ответ 6

Убедитесь, что свойства не являются нулевыми.

from a in this._addresses
where (a.Street != null && a.Street.Contains(street)) || 
(a.StreetAdditional != null && a.StreetAdditional.Contains(streetAdditional))
select a).ToList<Address>()

Если нулевая проверка является ложной, тогда второе предложение после && не будет оцениваться.

Ответ 7

from a in this._addresses
where a.Street.Contains(street) || (a.StreetAdditional != null && a.StreetAdditional.Contains(streetAdditional)
select a).ToList<Address>()

Ответ 8

Возможно, вы захотите проверить, чтобы переменные street и streetAdditional не были пустыми. Я просто столкнулся с одной и той же проблемой и установил их на пустую строку, казалось, решил мою проблему.

street = street ?? "";
streetAdditional = streetAdditional ?? "";
from a in this._addresses
where a.Street.Contains(street) || a.StreetAdditional.Contains(streetAdditional)
select a).ToList<Address>()

Ответ 9

Следует отметить, что сначала нужно оценить значение null.

where (**a.Street != null** && a.Street.Contains(street)) || (a.StreetAdditional != null && a.StreetAdditional.Contains(streetAdditional))
select a).ToList<Address>

()