2011-03-28 63 views
27

Khi tôi tạo một bảng tạm thời bằng cách sử dụng một select into trong SQL Server, có cách nào để chỉ định rằng một cột nên được nullable? Tôi có một quá trình nhiều bước mà tôi đang làm một bảng tạm thời bằng cách chọn rất nhiều cột (đó là lý do tại sao tôi không làm một create table #tmp (...)). Sau khi tôi thực hiện bảng tạm thời đó, tôi đang cập nhật một số cột và một số các bản cập nhật đó có thể vô hiệu hóa một trường.Tạo một cột có thể vô hiệu bằng cách sử dụng SQL Server SELECT INTO?

Tôi biết tôi có thể làm một tuyên bố alter table alter column để đạt được những gì tôi muốn, nhưng tôi tò mò về việc liệu có cách nào để xác định điều này trong chính bản thân số select hay không. Tôi biết bạn có thể nội tuyến cast các cột của bạn để có được kiểu dữ liệu mong muốn, nhưng tôi không thể thấy cách bạn chỉ định nullability.

Trả lời

22

Tính dễ vỡ được kế thừa từ cột nguồn.

Bạn có thể mất hoặc đạt được nullability với một biểu thức:

Ví dụ (literals liên tục xuất hiện để được vấn đề - cần một hàm NOOP tốt mà có thể trở lại 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 
+0

'NULLIF' dường như hoạt động tốt khi sử dụng cột. Câu trả lời của bạn khiến tôi nghĩ thử 'COALESCE (col_name, null)' mà nó hoạt động phổ biến mà không cần phải tạo ra một giá trị không thể. Tuy nhiên, có một tình huống khi không xuất hiện để làm việc, và đó là khi bạn đang chọn một chữ như 'select nullif ('asdf', '~') làm Giá trị thành _Test'. NULLIF/COALESCE có vẻ như nó đủ tốt, nhưng có cách nào khác hoạt động trong mọi tình huống không? – mattmc3

+0

@ mattmc3 - một số nhà khai thác phá vỡ (ví dụ, ABS hoạt động int eh ví dụ ở trên), nhưng NULLIF là không đủ. –

0

thời gian gần đây tôi đã cùng vấn đề - Tôi muốn sử dụng "chọn vào", muốn tất cả các cột trong bảng mục tiêu được nullable & một cách tiếp cận lặp lại mà tôi không phải biết tên của các trường trong bảng nguồn.

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 

nơi dbo.S_Data là bảng dữ liệu nguồn và [Z_ 1] & [Z _2] là hai cột giả sử dụng để tham gia

Sau đó, để dọn dẹp:

(a) Xóa hàng số trống

delete dbo.I_Data where [Z_1] = 1 

(b) Tháo fie giả lds:

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

Kính trọng.

10

soulution này thời gian gần đây tôi đã đi lên với và mặc dù tôi nên chia sẻ:

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

này có hiệu quả tạo ra một cấu trúc trùng lặp của SourceTable trong TargetTable với tất cả các cột nullable (ít nhất là trong SQL2008).

1

Nếu bạn muốn kế thừa nullablity cho cột đích bất kể cột bảng nguồn, bạn có thể làm theo truy vấn này.

SELECT COLUMN1, COLUMN2, COLUMN3 INTO DestinationTable from SourceTable 

nếu điều này là truy vấn của bạn, nơi COLUMN1, --COLUMN2, cột3 không nullable trong SourceTable sau đó thay đổi các truy vấn như

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

vậy, điều này sẽ cho phép bạn chèn các giá trị null trong bảng Destination .

+0

Phía bên trái của điều này là bạn sau đó phải thả bản ghi trống – UnhandledExcepSean

+0

Bản ghi trống nào? – Kilokahn

+0

Trong SQL Server, điều này làm cho cột trở thành kiểu int - mà không phải là mong muốn. – Kilokahn

1

Điều này cũng hoạt động.

select * 
into #so20150909 
from table 
where 1=0 
2

CONVERT sẽ làm cho cột của bạn không thể hoạt động và cũng hoạt động cho các hằng số/hằng số. Thử nghiệm trong 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 
Các vấn đề liên quan