2012-03-05 2 views
15

В нашем db есть таблица с чуть более 80 столбцами. Он имеет первичный ключ, а вставку Identity включен. Я ищу способ вставить в эту таблицу каждый столбец EXCEPT столбца первичного ключа из идентичной таблицы в другой БД.T-SQL Вставка в таблицу без указания каждого столбца

Возможно ли это?

+1

Вам нужно указать столбцы ... – JNK

+0

Звучит как случай ленивого программирования. Если вы щелкните правой кнопкой мыши по имени таблицы, вы можете «сценарий как -> вставить в», и все столбцы не идентичности будут написаны для вас. Shazam. –

+0

YoOu должен использовать производительность базы данных в долгосрочной перспективе не самостоятельно. Вы восприняли худший ответ на сгусток, потому что он удваивает работу каждый раз, когда он запускается над тем, что будет делать правильный запрос, и все, чтобы сэкономить немного времени. – HLGEM

ответ

40

Вы можете сделать это довольно легко на самом деле:

-- Select everything into temp table 
Select * Into 
    #tmpBigTable 
    From [YourBigTable] 

-- Drop the Primary Key Column from the temp table 
Alter Table #tmpBigTable Drop Column [PrimaryKeyColumn] 

-- Insert that into your other big table 
Insert Into [YourOtherBigTable] 
    Select * From #tmpBigTable 

-- Drop the temp table you created 
Drop Table #tmpBigTable 

условии, что вы имеете Удостоверение Вставить в «On YourOtherBigTable» и столбцы абсолютно идентичны вам будет хорошо.

+3

SELECT * - это антипаттерн. Это создает гораздо большую работу для сервера, чем правильную запись вставки с помощью столбцов. Это очень плохое решение. Вы делаете беспорядок производительности, чтобы сохранить десять секунд перетаскивания столбцов из объекта tbrowser. Это неприемлемая практика для профессионала. – HLGEM

+1

Также давайте не будем забывать, что в этом случае вы копируете всю таблицу во временную таблицу. Если у вас есть только несколько строк, это может сработать, но это может действительно привести в действие систему для таблицы с большим количеством строк. – Kibbee

+1

-1 по причинам, уже указанным @HLGEM. –

2

Вы можете запросить Information_Schema, чтобы получить список всех столбцов и программно сгенерировать имена столбцов для вашего запроса. Если вы все это делаете в t-sql, это будет громоздко, но это можно сделать. Если вы используете какой-либо другой язык клиента, например C# для выполнения операции, это будет немного менее громоздким.

2

Нет, это невозможно. У вас может возникнуть соблазн использовать

INSERT INTO MyLargeTable SELECT * FROM OtherTable 

Но это не сработает, потому что ваш столбец идентификации будет включен в *.

Вы можете использовать

SET IDENTITY_INSERT MyLargeTable ON 
INSERT INTO MyLargeTable SELECT * FROM OtherTable 
SET IDENTITY_INSERT MyLargeTable OFF 

сначала дают возможность вставляя значения идентификаторов, чем копировать записи, то снова включить столбец идентификаторов.

Но это не сработает. В этом случае сервер SQL не примет значение *. Вы должны явно включить Идентификатор в сценарий, например:

SET IDENTITY_INSERT MyLargeTable ON 
INSERT INTO MyLargeTable (Id, co1, col2, ...., col80) SELECT Id, co1, col2, ...., col80 FROM OtherTable 
SET IDENTITY_INSERT MyLargeTable OFF 

Итак, мы вернулись с того места, где мы начали.

Самый простой способ - щелкнуть правой кнопкой мыши по таблице в Studio Management Studio, позволить ей генерировать сценарии INSERT и SELECT и немного редактировать их, чтобы они работали вместе.

0

Действительно, для того, чтобы вытащить все столбцы из браузера объекта, честно, требуется десять секунд или меньше, а затем удалить столбец идентификатора из списка. Плохая идея использовать select * для чего угодно, кроме быстрого запроса ad hoc.

+2

Но что, если OP - это быстрый запрос ad hoc?;) – onedaywhen

+0

Что делать, если вы хотите сделать то же самое для всех ваших 1000 таблиц? И что, если список столбцов в таблице часто добавляется, и вы не хотите обновлять запрос каждый раз? –

+0

Вы должны обновлять запрос каждый раз, поскольку вам могут не понадобиться новые столбцы. Безответственно делать что-либо еще. В конечном итоге вы можете показать поля пользователей, которые им не только не нужны, но и не должны видеть. Или вы можете вставить вставки, которые помещают данные в неправильные столбцы, потому что кто-то изменил порядок столбцов в одной таблице, а не другой, или вставки, которые разбиваются, потому что новый столбец не был добавлен в таблицу, которая берет данные из выбранного. Возможно, вам придется настроить обновления для новых столбцов. Возможно, вам придется выяснить, какие данные будут собираться для вставок. – HLGEM

-1

В ответ на связанный с этим вопрос (SELECT * EXCEPT) я указываю, что действительно реляционный язык Tutorial D позволяет проекции выражать в терминах атрибутов, подлежащих удалению, вместо тех, которые должны храниться, например.

my_relvar { ALL BUT description } 

Однако его синтаксис INSERT требует значений кортежей конструкторы включают в себя атрибут пар имя/значение, например,

INSERT P 
    RELATION 
    { 
     TUPLE { PNO PNO ('P1') , PNAME CHARACTER ('Nut') }, 
     TUPLE { PNO PNO ('P2') , PNAME CHARACTER ('Bolt') } 
    }; 

Конечно, используя этот синтаксис не существует упорядоченность столбец (потому что это действительно реляционные!), Например, это семантически эквивалентно:

INSERT P 
    RELATION 
    { 
     TUPLE { PNO PNO ('P1') , PNAME CHARACTER ('Nut') }, 
     TUPLE { PNAME CHARACTER ('Bolt') , PNO PNO ('P2') } 
    }; 

Альтернативой было бы полностью полагаться на упорядочение атрибутов, которые SQL выполняет частично, например.это близко SQL-эквивалентно выше:

INSERT INTO P (PNO , PNAME) 
    VALUES   
     (PNO ('P1') , CAST ('Nut' AS VARCHAR (20))) , 
     (PNO ('P2') , CAST ('Bolt' AS VARCHAR (20))); 

После commalist колонн было указано, что VALUES строк конструкторы имеют поддерживать этот порядок, который не является идеальным. Но как минимум порядок указан: ваше предложение будет опираться на какой-то порядок по умолчанию, который может быть, возможно, недетерминированным.

3
CREATE TABLE Tests 
(
    TestID int IDENTITY PRIMARY KEY, 
    A int, 
    B int, 
    C int 
) 

INSERT INTO dbo.Tests 
VALUES (1,2,3) 

SELECT * FROM Tests 

Это работает в SQL2012

1

Почему бы не просто создать вид исходных данных, удаляя ненужные поля? Затем «Выберите * в» желание ваших сердец.

  • Локализованные управления в одном окне
  • Нет необходимости изменять SPROC
  • Добавить/изменить/удалить поля легко
  • Нет необходимости запрашивать мета-данные
  • Нет временных таблиц
+0

Почему создаются временные таблицы, перечисленные в качестве недостатка, или с использованием представления? Я не сомневаюсь в претензии, просто задаюсь вопросом о причине. –

+0

Таблица TEMP (может) использовать большой объем памяти/диска, где VIEW в основном фильтрует производственную таблицу в нужные поля. Этот метод будет работать быстрее, не будет иметь длительных накладных расходов и может быть изменен по желанию. – davidWazy

Смежные вопросы