Я хочу выполнить такой запрос
var result = from entry in table
where entry.something == null
select entry;
и получите IS NULL
сгенерированный.
Отредактировано: после первых двух ответов я чувствую необходимость уточнить, что я использую Entity Framework, а не Linq to SQL. Метод object.Equals () не работает в EF.
Редактировать № 2: вышеуказанный запрос работает как задумано. Он правильно генерирует IS NULL
. Однако мой производственный код был
value = null;
var result = from entry in table
where entry.something == value
select entry;
а сгенерированный SQL был something = @p; @p = NULL
. Кажется, что EF правильно переводит константное выражение, но если задействована переменная, она обрабатывает ее как обычное сравнение. На самом деле имеет смысл. Я закрою этот вопрос
.net
entity-framework
ado.net
Адриан Занеску
источник
источник
Ответы:
Обходной путь для Linq-to-SQL:
Обходной путь для Linq-to-Entities (ой!):
Это неприятный баг, который меня несколько раз кусал.
Если эта ошибка затронула и вас, посетите отчет об ошибке на UserVoice и сообщите Microsoft, что эта ошибка затронула и вас.Изменить: эта ошибка исправлена в EF 4.5 ! Спасибо всем за поддержку этой ошибки!
Для обратной совместимости это будет опция opt-in - вам нужно вручную включить настройку, чтобы она
entry == value
работала. Пока нет информации о том, что это за настройка. Быть в курсе!Изменить 2: Согласно этому сообщению команды EF, эта проблема была исправлена в EF6! Woohoo!
Это означает, что существующий код, который полагается на старое поведение (
null != null
но только при сравнении с переменной) , нужно будет либо изменить, чтобы не полагаться на это поведение, либо установитьUseCSharpNullComparisonBehavior
значение false, чтобы использовать старое нарушенное поведение.источник
(var result = from ...; if(value.HasValue) result = result.Where(e => e.something == value) else result = result.Where(e => e.something == null);
(where Object.Equals(entry.something,value))
Начиная с Entity Framework 5.0, вы можете использовать следующий код для решения вашей проблемы:
Это должно решить ваши проблемы, поскольку Entity Framerwork будет использовать сравнение NULL типа C #.
источник
Существует несколько более простой способ обхода, который работает с LINQ to Entities:
Это работает, потому что, как заметил AZ, LINQ to Entities особые случаи x == null (то есть сравнение равенства с нулевой константой) и преобразует его в x IS NULL.
В настоящее время мы рассматриваем возможность изменения этого поведения, чтобы автоматически вводить компенсирующие сравнения, если обе стороны равенства допускают значение NULL. Однако есть несколько проблем:
В любом случае, займемся ли мы этим, будет во многом зависеть от относительного приоритета, который придают ему наши клиенты. Если вас волнует эта проблема, я призываю вас проголосовать за нее на нашем новом сайте с предложениями функций: https://data.uservoice.com .
источник
Если это тип, допускающий значение NULL, может быть, попробовать использовать свойство HasValue?
Но здесь нет EF для тестирования ... просто предложение =)
источник
== null
ошибка все равно не попадает. Дело в том, чтобы выполнить фильтрацию по значению переменной, значение которой может быть нулевым, и чтобы нулевое значение находило нулевые записи.(x => x.Column == null)
работать. :)System.NullReferenceException
, поскольку объект уже нулевой!Ссылка MSDN : LINQ to SQL: встроенный в язык .NET запрос для реляционных данных
источник
чтобы иметь дело с нулевым сравнением, используйте
Object.Equals()
вместо==
проверьте эту ссылку
источник
null
,Object.Equals(null)
что делать , еслиObject
сам является недействительным?Указывая на то, что все предложения Entity Framework <6.0 генерируют неудобный SQL. См. Второй пример для "чистого" исправления.
Нелепое решение
приводит к SQL как:
Возмутительный обходной путь
Если вы хотите создать более чистый SQL, что-то вроде:
приводит к тому, что вы хотели в первую очередь:
источник
Вышеупомянутый запрос работает как задумано. Он правильно генерирует IS NULL. Однако мой производственный код был
и сгенерированный SQL был something = @p; @p = NULL. Кажется, что EF правильно переводит константное выражение, но если задействована переменная, она обрабатывает ее как обычное сравнение. На самом деле имеет смысл.
источник
Похоже, что у Linq2Sql тоже есть эта «проблема». Похоже, что для такого поведения есть веская причина из-за того, включены ли значения ANSI NULL или нет, но уму непостижимо, почему прямое «== null» на самом деле будет работать так, как вы ожидаете.
источник
Лично я предпочитаю:
над
потому что он предотвращает повторение - хотя это и неточно математически, но хорошо подходит для большинства случаев.
источник
Я не могу комментировать сообщение divega, но среди различных решений, представленных здесь, решение divega создает лучший SQL. И по производительности, и по длине. Я только что проверил с помощью SQL Server Profiler и посмотрел на план выполнения (с «УСТАНОВИТЬ ПРОФИЛЬ СТАТИСТИКИ ВКЛ»).
источник
К сожалению, в Entity Framework 5 DbContext проблема все еще не устранена.
Я использовал этот обходной путь (работает с MSSQL 2012, но параметр ANSI NULLS может быть устаревшим в любой будущей версии MSSQL).
Следует отметить, что это грязный обходной путь, но он может быть реализован очень быстро и работает для всех запросов.
источник
Если вы предпочитаете использовать синтаксис метода (лямбда), как я, вы можете сделать то же самое, например:
источник
использовать это
источник