¿Crear una columna anulable usando SQL Server SELECT INTO?


Cuando creo una tabla temporal usando un select into en SQL Server, ¿hay alguna manera de especificar que una columna debe ser nullable? Tengo un proceso de varios pasos donde estoy haciendo una tabla temporal seleccionando muchas columnas (por lo que no estoy haciendo un create table #tmp (...)). Después de hacer esa tabla temporal, estoy actualizando algunas columnas y algunas de esas actualizaciones podrían anular un campo.

Sé que podría hacer una declaración alter table alter column para lograr lo que quiero, pero tengo curiosidad sobre si hay una manera de especificar esto en el select en sí. Sé que puede insertar cast sus columnas para obtener el tipo de datos deseado, pero no puedo ver cómo especifica la nullabilidad.

Author: mattmc3, 2011-03-29

6 answers

Null, se hereda de la columna de origen.

Puede perder o ganar nullability con una expresión:

Ejemplo (los literales constantes parecen ser problemáticos - necesitan una buena función NOOP que pueda devolver NULL):

CREATE TABLE SO5465245_IN
    (
     a INT NOT NULL
    ,b INT NULL
    ) ;
GO

SELECT  COALESCE(a, NULL) AS a
       ,ISNULL(b, 0) AS b
       ,COALESCE(10, NULL) AS c1
       ,COALESCE(ABS(10), NULL) AS c2
       ,CASE WHEN COALESCE(10, NULL) IS NOT NULL THEN COALESCE(10, NULL) ELSE NULL END AS c3
INTO    SO5465245_OUT
FROM    SO5465245_IN ;
GO

SELECT  TABLE_NAME
       ,COLUMN_NAME
       ,IS_NULLABLE
FROM    INFORMATION_SCHEMA.COLUMNS
WHERE   TABLE_NAME LIKE 'SO5465245%'
ORDER BY TABLE_NAME
       ,ORDINAL_POSITION ;
GO

DROP TABLE SO5465245_IN ;
GO

DROP TABLE SO5465245_OUT ;
GO
 24
Author: Cade Roux,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-03-28 23:39:45

Esta soulution que he llegado recientemente con y aunque debería compartir:

select top 0
  B.*
into
  TargetTable
from
  SourceTable as A
    left join SourceTable as B on 1 = 0

Esto crea efectivamente una estructura duplicada de SourceTable en TargetTable con todas las columnas nullables (al menos en sql2008).

 10
Author: Kuba Wyrostek,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-12-03 10:20:57

CONVERT hará que tus columnas sean nullables, y también funciona para literales/constantes. Probado en SQL Server 2005/2008.

SELECT 
    SomeText = CONVERT(varchar(10), 'literal'),
    SomeNumber = CONVERT(int, 0)
INTO SO5465245

INSERT SO5465245 VALUES (null, null)

SELECT TABLE_NAME, COLUMN_NAME, DATA_TYPE, IS_NULLABLE
FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_NAME = 'SO5465245'
ORDER BY TABLE_NAME, ORDINAL_POSITION

DROP TABLE SO5465245
 2
Author: wezzix,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-03-24 18:54:14

Si desea heredar nullablity para la columna de destino independientemente de las columnas de la tabla de origen, puede seguir esta consulta.

SELECT COLUMN1, COLUMN2, COLUMN3 INTO DestinationTable from SourceTable

Si esta era su consulta donde COLUMN1, COLUMN2, COLUMN3 no eran nullable en SourceTable, cambie la consulta como

SELECT NULL COLUMN1, NULL COLUMN2, NULL COLUMN3 INTO DestinationTable from SourceTable

Por lo tanto, esto le permitirá insertar valores nulos en la tabla de destino.

 1
Author: SantoshG,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-09-09 12:24:35

Esto también funciona.

select *
into #so20150909
from table
where 1=0
 1
Author: UnhandledExcepSean,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-09-09 12:53:39

Recientemente tuve el mismo problema: quería usar "seleccionar en", quería que todas las columnas de la tabla de destino fueran nullables y un enfoque repetible donde no tenía que saber los nombres de los campos en la tabla de origen.

select *
into dbo.I_Data
from
  (select 1[Z_1]) A
  full join (select null[Z_2], * from dbo.S_Data) B on A.Z_1 = B.Z_2

Donde dbo.S_Data es la tabla de datos de origen y [Z_ 1] & [Z _2] son dos columnas ficticias utilizadas para la combinación

Luego para limpiar:

(a) Eliminar la fila de nulos

delete dbo.I_Data where [Z_1] = 1

(b) Retire el maniquí campos:

alter table dbo.I_Data 
  drop column [Z_1], [Z_2]

Saludos.

 0
Author: David P Reynevich,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-05-21 13:29:28