How will this below query execute and is there a better way to write this query?
INSERT INTO tableName
SELECT *
INTO tableName
FROM tableName
I would use:
INSERT INTO tableName (col1, col2, col3)
SELECT col1, col2, col3
FROM someOtherTable;
Note that you should generally always explicitly specify which columns you want both for the insert and the select. While your code might run as is, it is prone to breaking should the structure for either table change in the future.
Related
I have a SQL Server database with a table with 20 columns. These columns have data as agree or disagree. Now I want to show rows in these columns which have "agree" data in them. I can use where clause but it is a time consuming task for 20 columns. I am looking for a SQL query which does this task.
You can use in:
select t.*
from t
where 'agree' in (col1, col2, ... col20);
There is no shortcut for this type of scenarios, If you want to compare all the columns, you have to explicitly mention each and every column like .
WHERE Col1='agree' AND Col2="agree"....
To avoid coding, you may go with dynamic query creation or creating a function, but ultimately it will be executed as same query comparing all the columns.
What about JOIN ?
If u have such a complex logic, best practices advise to keep data in different tables.
Here's some simplified example code that tests out several methods to return records that may or may not agree.
Just for the fun of it actually.
declare #T table (id int identity(1,1) primary key, col1 varchar(30), col2 varchar(30), col3 varchar(30));
insert into #T (col1, col2, col3) values
('agree','agree','agree'),
('agree','disagree','disagree'),
('agree','disagree',null),
('disagree','disagree','disagree'),
('disagree','disagree',null),
(null,null,null);
select 'OR' as method, * from #T
where (col1='agree' OR col2='agree' OR col3='agree');
select 'AND' as method, * from #T
where (col1='agree' AND col2='agree' AND col3='agree');
select 'IN' as method, * from #T
where 'agree' IN (col1, col2, col3);
select 'NOT IN' as method, * from #T
where 'agree' NOT IN (col1, col2, col3);
select 'LIKE' as method, * from #T
where CONCAT('-',col1,'-',col2,'-',col3,'-') LIKE '%-agree-%';
select 'NOT LIKE' as method, * from #T
where CONCAT('-',col1,'-',col2,'-',col3,'-') NOT LIKE '%-agree-%';
select 'ALL' as method, * from #T
where 'agree' = ALL(select col from (values (col1),(col2),(col3))q(col));
select 'SOME' as method, * from #T
where 'agree' = SOME(select col from (values (col1),(col2),(col3))q(col));
select 'ANY' as method, * from #T
where 'agree' = ANY(select col from (values (col1),(col2),(col3))q(col));
select 'EXISTS' as method, * from #T
where EXISTS (
select 1
from (values (col1),(col2),(col3))q(col)
where col = 'agree'
);
select 'NOT EXISTS' as method, * from #T
where NOT EXISTS (
select 1
from (values (col1),(col2),(col3))q(col)
where col = 'agree'
);
I'm currently inserting into a table with the following prefix but also manaully set what i want in the last 2 columns ( 1,getdate() )
Insert into [Table1]
select col1,col2,col3, 1,getdate()
from [table2]
Issue is there are loads of columns and causing a mess in the SP.
I've tried to rewrite the statement with...
Insert Into [table1]
Select * from [Table2]
But I also need to take into consideration I want to manually write into those 2 columns..
Is there a way of doing this ?
Many Thanks
This might solve your issue:
Insert into [Table1]
select col1, col2, col3, '1' as [col4] , getdate() as [col5] from [table2]
Two points. First, when using insert you should always be in the habit of naming the columns for the insert:
Insert into [Table1](col1, col2, col3, col4, col5)
select col1, col2, col3, 1, getdate()
from [table2];
Second, you do not have to put getdate() in the insert. Let the database do the work for you with a default value:
create table table1 . . .
col5 date default getdate()
);
When use a bunch of INSERT statements as below it takes forever :
INSERT INTO my_table ( col1, col2, id_col) VALUES ('val1', 'val1', (select max(my_table_ID) from my_table)+1);
If I run one by one and commit then it works fine. What is the reason?
I know sequence should be used in production. But I am writing this to insert few rows in toad.
may be
INSERT INTO my_table ( col1, col2, id_col)
VALUES ('val1', 'val1', (select max(my_table_ID)+1 from my_table));
or in pl/sql block
declare
v_max number(10);
begin
select max(my_table_id) + 1 into v_max
from my_table;
insert into my_table ( col1, col2, id_col)
values ('val1', 'val1', v_max);
end;
/
but, i don't know you task...
may be used sequence + trigger before insert?
I'm doing an
INSERT INTO table1...
SELECT...
FROM table2
However, I need to retrieve the identity from a table3 and do an insert into it just before inserting into table1. These two inserts need to occur together, with table3 insert going first. I've tried something like this:
INSERT INTO table1 (col1, col2, col3)
SELECT (
col1=(insert into table3(col1, col2)values(1,1) select SCOPE_IDENTITY(),
col2, col3)
FROM table2
But that doesn't work. table1.col1 does need the identity value from the new insert into table3. Amount of data to insert probably no more than a few 100 rows. Any suggestions?
It looks like you might be able to use the Output Clause.
BEGIN TRANSACTION
DECLARE #MyResults table(col1 int, col2 int, col3 int);
INSERT INTO table3 (col1, col2)
OUTPUT SCOPE_IDENTITY(), table2.col2, table2.col3 INTO #MyResults
SELECT 1, 1 FROM table2
INSERT INTO table1 (col1, col2, col3)
SELECT col1, col2, col3 FROM #MyResults
COMMIT
I am trying to run this script:
SET IDENTITY_INSERT dbo.Message ON
INSERT INTO dbo.Message
SELECT (Values I want to insert)
and when I do I still get the error
*An explicit value for the identity column in table 'dbo.Message' can only be specified when a column list is used and IDENTITY_INSERT is ON.*
What am I doing wrong?
The key to your error is "when a column list is used". You want:
SET IDENTITY_INSERT dbo.Message ON
INSERT INTO dbo.Message (column1, column2, ...) -- Added column list here
SELECT (Values I want to insert)
You need to do just as the error message says. Format your code like:
INSERT INTO dbo.Message
(col1, col2, col3, col4)
SELECT Col1, col2, col3, col4
FROM OtherTable
You need the list of fields after the INSERT line, and you need to specify the field names in your SELECT - SELECT * won't work.
You have to mention all the columns Name in both Insert Statement and in select clause.
Some thing like this.
Insert Into tbl
(
[col1],
[col2]
)
SELECT
[col1],
[col2]