I want to have values in a column in particular series
10100
10200
10300
.
.
.
.
11000
11100
11200
.
.
How to do this ? I think while loop would be used
insert into mytable(col_name)
select <>
You can do this:
WITH Temp
AS
(
SELECT digit
FROM (VALUES(0),(1),(2),(3),(4),(5),(6),(7),(8),(9)) AS temp(digit)
), Nums
AS
(
SELECT t3.digit * 100 + t2.digit * 10 + t1.digit + 1 AS id
FROM TEMP AS t1
CROSS JOIN TEMP AS t2
CROSS JOIN TEMP AS t3
)
SELECT
n = 10100 + (id - 1) * 100
from nums
ORDER BY n;
SQL Fiddle Demo
How this works?
This query will give you 1000 rows for the sequence you are looking for, which is called Arithmetic progression, and in your sequence the nth term of the sequence is given by A + (n - 1) * d. In your sequence: a = 10100 the first number, the starting number, d = 100 which is the seed.
First, I used an anchor query which generate 10 numbers, (note that this syntax is new to SQL Server 2008),
then I cross joined it with itself 3 times giving me 103 rows = 1000 rows I used them to generate 1000 numbers of this sequence based on the rule: each n number = A + (n - 1) * d , if you need more cross join it with it self more times.
You can then insert them into a new table, just do INSERT INTO SELECT, instead of just SELECT.
Note that: You might need to use IDENTITY column instead of all this stuff, using it you can define a starting value and a seeding value, then it will be incremented automatically, see this article:
Understanding Identity Columns
Please try this:
DECLARE #table as TABLE(NUM bigint)
declare #var bigint
set #var=10100
while #var<11200
begin
insert into #table values (#var)
set #var=#var+100
end
select * from #table
Related
I've got a SQL query for inserting data into a table consisting of values for StorageRowNo and StorageID. The goal is to repeat this query a specified number of times with StorageRowNo increasing by 1 every time the query is repeated. Any input would be greatly appreciated!
INSERT [dbo].[StorageRow]
SELECT StorageRowNo, StorageID
FROM (VALUES (1, 2)) V (StorageRowNo, StorageID)
WHERE NOT EXISTS (SELECT 1
FROM [dbo].[StorageRow] C
WHERE C.StorageRowNo = V.StorageRowNo
AND C.StorageID = V.StorageID);
Expected output would be something like this if the specified number were 3.
StorageRowNo
StorageID
1
2
2
2
3
2
use straight sql if you can
DECLARE #numRepeats INT = 10; -- number of times to repeat the query
INSERT [dbo].[StorageRow]
SELECT V.StorageRowNo, V.StorageID
FROM (select row_number() over(order by (select null)) as StorageRowNo
,2 as StorageID
from master..spt_values
) V
WHERE NOT EXISTS (SELECT 1
FROM [dbo].[StorageRow] C
WHERE C.StorageRowNo = V.StorageRowNo
AND C.StorageID = V.StorageID);
AND V.StorageRowNo<=#numRepeats
I have a SQLite file and I want to add 2550 empty (NULL) rows.
I am able to add one empty line with this code
INSERT INTO my_table DEFAULT VALUES
But I need 2550 rows. Is there any shortcut for it? I don't want to execute same code 2550 times.
If your version of SQLite support it, you could use a recursive CTE to generate a series from 1 to 2550, and then insert "empty" records along that sequence:
WITH RECURSIVE generate_series(value) AS (
SELECT 1
UNION ALL
SELECT value + 1
FROM generate_series
WHERE value + 1 <= 2550
)
INSERT INTO yourTable (col1, col2, ...)
SELECT NULL, NULL, ...
FROM generate_series;
It is not clear which values, if any, you want to specify for the actual insert. If you omit mention of any column in the insert, then by default SQLite should assign NULL or whatever default value be defined for that column.
If your table is empty, then use a recursive CTE to get 2550 rows each consisting of the integers 1 to 2550 and use them to insert 2550 rows:
WITH cte AS (
SELECT 1 nr
UNION ALL
SELECT nr + 1
FROM cte
WHERE nr < 2550
)
INSERT INTO my_table(rowid)
SELECT nr FROM cte
This way, you use the column rowid where the integer values of the CTE will be stored and there is no need to enumerate all the columns of your table in the INSERT statement. These columns will get their default values.
If your table is not empty you can do it in a similar way by starting the integer numbers from the max rowid value in the table +1:
WITH cte AS (
SELECT MAX(rowid) + 1 nr FROM my_table
UNION ALL
SELECT nr + 1
FROM cte
WHERE nr < (SELECT MAX(rowid) + 2550 FROM my_table)
)
INSERT INTO my_table(rowid)
SELECT nr FROM cte
See a simplified demo (for 5 rows).
But since you also tagged android-sqlite you can use a for loop:
for (int i = 1; i <= 2550; i++) {
db.execSQL("INSERT INTO my_table DEFAULT VALUES");
}
where db is a valid non null instance of SQLiteDatabase.
You can generate numbers using a recursive CTE and then insert . . . but you need to be more explicit about the values being inserted:
with cte as (
select 1 as n
union all
select n + 1
from cte
where n < 2550
)
insert into mytable (<something>)
select <something>
from cte;
I think you need to specify the value for at least one column in SQLite.
I am looking to create a table that has 100 rows, and the first column is organized by the letters A-Z, and repeats all the way to 100. The closest I have come is either:
having a numeric column that then uses the ASCII values to convert the number to the letter, however this involves creating the numeric column first, and then having the alphabet column dependent on this one, or
I have been able to create a single column, however when I try to print the whole table, it shows up as AAAA, BBBB, CCCC, DDDD, etc.
I need the column to be completely independent which is why solution #1 doesn't work, and I can't find a way to properly sort or organize solution #2 for it to be A, B, C instead of the way it is printing now. Screenshots for context:
Solution 1
Solution 2
I have been using this code to create the table:
SELECT n
FROM (VALUES (0),(1),(2),(3),(4),(5),(6),(7),(8),(9)) t(n)
)
SELECT n1.n + n10.n * 10 as col
INTO dbo.table1
FROM nums n1
CROSS JOIN nums n10;
Then for solution 1, I tried this:
ALTER TABLE numbers
ADD letters AS CHAR(num % 26 + 65);
SELECT * FROM numbers
ORDER BY num;
and for solution 2, this:
ALTER TABLE table1
ALTER COLUMN col VARCHAR(3);
UPDATE table1
SET col = col % 26 + 65;
UPDATE table1
SET col = CHAR(col);
SELECT * FROM table1
ORDER BY col;
I have been at this for a few hours now, trying different things in both solutions to get the answer.
Thanks in advance.
If you want to repeatedly cycle through generating letters, you can use a recursive CTE:
with cte as (
select convert(varchar(max), 'A') as letter, 1 as n
union all
select (case when letter < 'Z' then convert(varchar(max), char(ascii(letter) + 1)) else 'A' end),
n + 1
from cte
where n < 100
)
select letter
from cte;
You can use insert or select into to put the values in a table.
If you want more than 100 rows, you'll need to add option (maxrecursion 0).
There is no certain order of rows in a table. Even if the table has a clustered index specified. Such a concept does not exist in relational databases.
To ensure a specific order of values you need to force it using ORDER BY clause in a SELECT statement.
Considering that, the following code must give you an idea how to implement your solution:
With nums as (
SELECT n
FROM (VALUES (0),(1),(2),(3),(4),(5),(6),(7),(8),(9)) t(n)
),
numbers as (
SELECT n1.n + n10.n * 10 as num
FROM nums n1
CROSS JOIN nums n10
)
select num, char(num/26 + 65) + CHAR(num % 26 + 65)
from numbers
order by num
I have a table and i would like to replicate/clone records within the same table. However i would like to do that with a condition. And the condition is i have a column called recordcount with numeric values. For example Row 1 can take on a value of recordcount say 7, then i would like my row 1 to be replicated 7 times. Row 2 could take on a value say 9 then i would like row 2 to be replicated 9 times.
Any help is appreciated. Thank you
What you can do (and I'm pretty sure it's not a best practice),
Is to hold a table with just numbers, which has rowcount that correspond to the numeric value.
Join that with your table, and project your table only.
Example:
create table nums(x int);
insert into nums select 1;
insert into nums select 2;
insert into nums select 2;
insert into nums select 3;
insert into nums select 3;
insert into nums select 3;
create table t (txt varchar(10) , recordcount int);
insert into t select 'A',1;
insert into t select 'B',2;
insert into t select 'C',3;
select t.*
from t
inner join nums
on t.recordcount = nums.x
order by 1
;
Will project:
"A",1
"B",2
"B",2
"C",3
"C",3
"C",3
I have a small SQL based challenge that i'm trying to solve to better my knowledge of Dynamic SQL.
My requirements are as follows.
I created a table that looks as follows:
CREATE TABLE Prison_Doors
(
DoorNum INT IDENTITY(1,1) PRIMARY KEY,
DoorOpen BIT,
DoorClosed BIT,
Trips INT
)
GO
I need to Create a Dynamic SQL Proc to insert 50 Door numbers and assign them as closed.
Expected result of proc:
|DoorNum|DoorOpen|DoorClosed|Trips|
|-------|--------|----------|-----|
| 1 | 0 | 1 |null |
|-------|--------|----------|-----|
|---------All the way to 50-------|
|-------|--------|----------|-----|
| 50 | 0 | 1 |null |
This is what I have written but it is not inserting:
BEGIN
DECLARE #SQL VARCHAR(8000)
DECLARE #Index INT
SET #Index=1
WHILE (#Index<=50)
BEGIN
SET #SQL= 'INSERT INTO Prison_Doors(DoorNum,DoorOpen,DoorClosed)
VALUES('+CAST(#Index AS VARCHAR)+',0,1),'
SET #Index=#Index+1
END
SET #SQL = SUBSTRING(#SQL, 1, LEN(#SQL)-1)
EXEC(#SQL)
END
I would like to know what I am doing wrong.
after all of this is done I then need to run another loop to start at door one and change every second door to open and change trips to one and then increment to every 3 doors to open and trips becomes 2 and this incrementation continues until all doors are open which will then select the number of trips that it took.
I hope somebody can assist me with this as I am new to Dynamic SQL and I just need some guidance and not the complete solution.
Help is much appreciated :)
The error you got is because you are trying to insert into an identity column DoorNumber:
DoorNum INT IDENTITY(1,1) PRIMARY KEY,
Remove that columns from the column list, instead of:
INSERT INTO Prison_Doors(DoorNum,DoorOpen,DoorClosed)
remove that column DoorNum:
INSERT INTO Prison_Doors(DoorOpen,DoorClosed)
...
However, there is no need for dynamic SQL to do that, you can do this using an anchor table like this:
WITH temp
AS
(
SELECT n
FROM (VALUES(1), (2), (3), (4)) temp(n)
), nums
AS
(
SELECT ROW_NUMBER() OVER(ORDER BY (SELECT 1)) AS n
FROM temp t1, temp t2, temp t3
)
INSERT INTO Prison_Doors(DoorOpen, DoorClosed)
SELECT 0 AS DoorOpen, 1 AS DoorClosed
FROM nums
WHERE n <= 50;
Live Demo.
Update:
What my code does line by line?
Generating Sequence of numbers:
The first problem was generating a sequence of 50 numbers from 1 to 50, I used an anchor table with only four rows from 1 to 4 like this:
SELECT n
FROM (VALUES(1), (2), (3), (4)) temp(n);
This syntax using the VALUES is new to SQL-Server-2008, it is called Row Value Constructor. After the VALUES, you assign an alias of the table and the target columns in parentheses like temp(n).
For old versions you have to use something like :
SELECT n
FROM
(
SELECT 1 AS n
UNION ALL
SELECT 2
UNION ALL
SELECT 3
UNION ALL
SELECT 4
) AS temp;
This will give you only 4 rows, but we need to generate 50. Thats why I CROSS JOIN this table three time with itself using:
FROM temp t1, temp t2, temp t3
It is the same as
FROM temp t1
CROSS JOIN temp t2
CROSS JOIN temp t3
This will multiply these rows 64 times, 4 rows3 = 64 rows:
1 1 1
1 2 1
1 3 1
1 4 1
2 1 1
2 2 1
2 3 1
2 4 1
....
3 1 4
3 2 4
3 3 4
3 4 4
4 1 4
4 2 4
4 3 4
4 4 4
The Use Of ROW_NUMBER() Function:
Then using the ROW_NUMBER() will give us a ranking number from 1 to 64 like this:
WITH temp
AS
(
SELECT n
FROM (VALUES(1), (2), (3), (4)) temp(n)
)
SELECT ROW_NUMBER() OVER(ORDER BY (SELECT 1)) AS n
FROM temp t1, temp t2, temp t3;
Note that: ROW_NUMBER requires an ORDER BY clause, in or case it doesn't matter the order, so I used (SELECT 1).
There is also another way for generating a sequence numbers with out the use of ROW_NUMBER, it also depends on the CROSS JOIN, with an anchor table like:
WITH temp
AS
(
SELECT n
FROM (
VALUES(0), (1), (2), (3), (4), (5), (6), (7), (8), (9)
) temp(n)
), nums
AS
(
SELECT t1.n * 100 + t2.n * 10 + t3.n + 1 AS n
FROM temp t1, temp t2, temp t3
)
SELECT n
FROM nums
ORDER BY n;
Another Way of Generating Sequence Of Numbers
Common Table Expressions:
The CTE is called common table expression, and it was introdeced in SQL Server 2005. It is one of the table expressions types that SQL Server supports. The other three are:
Derived tables,
Views, and
Inline table-valued functions.
It has a lot of important advantages. One of them is let you create a virtual tables that you can reuse them later, like what I did:
WITH temp
AS
(
SELECT n
FROM (VALUES(1), (2), (3), (4)) temp(n)
), nums
AS
(
SELECT ROW_NUMBER() OVER(ORDER BY (SELECT 1)) AS n
FROM temp t1, temp t2, temp t3
)
...
Here I defined two CTE's temp then another one nums that ruse that temp so this OL, you can create multiple CTE's, just put a semicolon, then a new one with the AS clause and two ().
Insert into one table from another table using INSERT INTO ... SELECT ...
Now, we have a virtual table nums having rows from 1 to 64, we need to insert the rows from 1 to 50.
For this, you can use the INSERT INTO ... SELECT ....
Note that the columns in the INSERT clause are optional, but If you do so, you have to put a value for each row, if not you will got an error, for example if you have four columns and you put only three values in the VALUES clause or in the SELECT clause, then you will got an error. This is not valid for the idenetityt columns which are defined with:
Identity(1,1)
^ ^
| |
| ------------------The seed
The start
In this case you simply ignore that column in the columns list in the INSERT clause and it will have the identity value. There is an option that let you insert a value manually like in the #Raj's answer.
Note that: In my answer, I am not inserting the sequence numbers in to that column instead, inserting the values 50 times. But the actual numbers are generating automatically because of the Identity column:
...
INSERT INTO Prison_Doors(DoorOpen, DoorClosed)
SELECT 0 AS DoorOpen, 1 AS DoorClosed
FROM nums;
WHERE n <= 50;
Firstly, you have declared DoorNum as Identity and then you are trying to explicitly insert values into that column. SQL Server does not allow this, unless you choose to
SET IDENTITY_INSERT ON
Try this query. It should insert the 50 rows you want
DECLARE #SQL VARCHAR(8000)
DECLARE #Index INT
SET #Index=1
WHILE (#Index<=50)
BEGIN
SET #SQL= 'INSERT INTO Prison_Doors(DoorOpen,DoorClosed)VALUES(0,1)'
EXEC(#SQL)
SET #Index=#Index+1
END
Raj