2010-05-26 2 views
64

Я создаю вычисляемый столбец в полях, некоторые из которых потенциально нулевые.Конкатенация строки SQL Server с помощью Null

Проблема в том, что если любое из этих полей равно null, весь вычисленный столбец будет равен нулю. Я понимаю из документации Microsoft, что это ожидается и может быть отключен с помощью параметра SET CONCAT_NULL_YIELDS_NULL. Однако я не хочу изменять это поведение по умолчанию, потому что я не знаю его последствий для других частей SQL Server.

Есть ли способ проверить, является ли столбец нулевым и только добавить его содержимое в формулу вычисленного столбца, если оно не является нулевым?

ответ

110

Вы можете использовать ISNULL(....)

SET @Concatenated = ISNULL(@Column1, '') + ISNULL(@Column2, '') 

Если значение столбца/выражение действительно NULL, то указанный (здесь: пустая строка), второе значение будет использоваться вместо этого.

+13

«Coalesce» - это стандартное имя функции ANSI, но ISNULL легче записать. –

+1

И ISNULL, похоже, немного медленнее на SQL Server, поэтому, если вы хотите использовать его в функции, которая объединяет строки в вычисленный столбец, вы можете отказаться от стандарта ANSI и выбрать скорость (см. Adam Machanic: http: //sqlblog.com/blogs/adam_machanic/archive/2006/07/12/performance-isnull-vs-coalesce.aspx) –

+0

Только что использовал этот запрос Isnull (,), он много помогал, поскольку я объединял значения вместе, и если один из них был нулевым, все тоже стало нулевым. – Sizons

27

COALESCE. Вместо your_column используйте COALESCE(your_column, ''). Это вернет пустую строку вместо NULL.

0

В Sql Server:

insert into Table_Name(PersonName,PersonEmail) values(NULL,'[email protected]') 

PersonName is varchar(50), NULL is not a string, because we are not passing with in single codes, so it treat as NULL. 

Код За:

string name = (txtName.Text=="")? NULL : "'"+ txtName.Text +"'"; 
string email = txtEmail.Text; 

insert into Table_Name(PersonName,PersonEmail) values(name,'"+email+"') 
7

Я просто хотел, чтобы внести свой вклад в этом кто-то должен искать помощи с добавлением разделителей между строк, в зависимости от является ли поле NULL или нет.

Таким образом, в примере создания адреса из одной строки из отдельных полей

Адрес1, Адрес2, Address3, Город, Postcode

в моем В случае, у меня есть следующая расчетная колонка, которая, кажется, работает так, как я ее хочу:

case 
    when [Address1] IS NOT NULL 
    then (((   [Address1]  + 
      isnull(', '+[Address2],'')) + 
      isnull(', '+[Address3],'')) + 
      isnull(', '+[City] ,'')) + 
      isnull(', '+[PostCode],'') 
end 

Надеюсь, что кто-то поможет!

+0

Там есть довольно много избыточного вложенного брекетинга, который можно удалить. Еще один совет: вы также можете удалить оператор case, как если бы адрес1 был пустым, все выражение будет оцениваться как null (хотя наличие case case делает обратное внимание, что это может произойти) – Alternator

38

С SQL Server 2012 это намного проще с помощью функции CONCAT.

Он обрабатывает NULL как пустая строка

DECLARE @Column1 VARCHAR(50) = 'Foo', 
     @Column2 VARCHAR(50) = NULL, 
     @Column3 VARCHAR(50) = 'Bar'; 


SELECT CONCAT(@Column1,@Column2,@Column3); /*Returns FooBar*/ 
+0

Спасибо! Это то, что мне нужно! – Shiva

+0

Для более старых версий вы получаете сообщение «CONCAT» не является признанным встроенным именем функции », поэтому используйте COALESCE – Savage

7

Вы также можете использовать CASE - мой код ниже проверяет как нулевые значения и пустые строки, и добавляет Seperator только если имеется значение следовать:

SELECT OrganisationName, 
'Address' = 
CASE WHEN Addr1 IS NULL OR Addr1 = '' THEN '' ELSE Addr1 END + 
CASE WHEN Addr2 IS NULL OR Addr2 = '' THEN '' ELSE ', ' + Addr2 END + 
CASE WHEN Addr3 IS NULL OR Addr3 = '' THEN '' ELSE ', ' + Addr3 END + 
CASE WHEN County IS NULL OR County = '' THEN '' ELSE ', ' + County END 
FROM Organisations 
10

Использование

SET CONCAT_NULL_YIELDS_NULL OFF 

и конкатенация нулевых значений на ст ring не приведет к null.

Обратите внимание, что это устаревшая опция, не используйте. Для получения более подробной информации см. documentation.

0

У меня было много проблем с этим. Не удалось заставить его работать, используя конкретные примеры выше, но это делает работу для меня:

Replace(rtrim(ltrim(ISNULL(Flat_no, '') + 
' ' + ISNULL(House_no, '') + 
' ' + ISNULL(Street, '') + 
' ' + ISNULL(Town, '') + 
' ' + ISNULL(City, ''))),' ',' ') 

Заменить исправляет двойные пробелы, вызванные конкатенации одиночные пробелы ни с чем между ними. r/ltrim избавляется от любых пробелов на концах.