Query to create a table with blank row inserted between missing RowID's?
(1) By anonymous on 2022-08-18 00:32:44 [link] [source]
Hi ALL, I would like to insert a blank row or a new row with just a character or symbol in place of missing rowID's
So for instance, I have currently got:
RowID
1 xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx 2 xxxxxxxxxxxxx 3 xxxxxxxxxxxxxxx 4 xxxxxxxxxxxxxxxxxxxxxxxxxxxx 6 xxxxxxxxxxxxxxxx 9 xxxxx 10 xxxxxxxxxxxxx 11 xxxxxxxxxxxx 12 xxxxx 19 xxxxxxxxxxxxxxxxxxxxxxxxxx 20 xxxxxxxxxxx 21 xxxxxxxxxxxxxxxxxxxxxxxx
and I would like to create a table formatted like this
1 xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx 2 xxxxxxxxxxxxx 3 xxxxxxxxxxxxxxx 4 xxxxxxxxxxxxxxxxxxxxxxxxxxxx 5 (deleted) 6 xxxxxxxxxxxxxxxx 7 (Deleted) 8 (Deleted) 9 xxxxx 10 xxxxxxxxxxxxx 11 xxxxxxxxxxxx 13 (Deleted) 12 xxxxx 13 (Deleted) 14 (Deleted) 15 (Deleted) 16 (Deleted) 17 (Deleted) 18 (Deleted) 19 xxxxxxxxxxxxxxxxxxxxxxxxxx 20 xxxxxxxxxxx 21 xxxxxxxxxxxxxxxxxxxxxxxx
The database is a fairly large sms.db (110mb) and the table is the "messages" table.
I have tried putting together query's to achieve this but keep falling down with them!
Anyone able to make light work of what I have been banging my head against a wall with for days?
Thankyou!
(2) By jake on 2022-08-18 01:14:22 in reply to 1 [link] [source]
CREATE TABLE t(id INTEGER PRIMARY KEY, message);
-- generate odd ids
INSERT INTO t
SELECT value, 'x'
FROM generate_series(1, 10, 2);
-- fill gaps
INSERT INTO t
SELECT value, 'deleted'
FROM generate_series((SELECT Min(id) FROM t), (SELECT Max(id) FROM t))
WHERE NOT EXISTS (SELECT * FROM t WHERE id = value);
.mode box
SELECT *
FROM t;
┌────┬─────────┐
│ id │ message │
├────┼─────────┤
│ 1 │ x │
│ 2 │ deleted │
│ 3 │ x │
│ 4 │ deleted │
│ 5 │ x │
│ 6 │ deleted │
│ 7 │ x │
│ 8 │ deleted │
│ 9 │ x │
└────┴─────────┘
(5) By anonymous on 2022-08-18 02:17:30 in reply to 2 [link] [source]
Thankyou
(3) By JayKreibich (jkreibich) on 2022-08-18 01:28:15 in reply to 1 [link] [source]
You want to generate a series and then use a LEFT JOIN
to fill in the blanks.
DROP TABLE IF EXISTS v;
CREATE TABLE v
(
id INTEGER PRIMARY KEY NOT NULL,
value TEXT
);
INSERT INTO v VALUES
( 1, 'a'),
( 5, 'e'),
( 6, 'f'),
(10, 'j');
SELECT
s.value AS id,
ifnull(v.value, '(DELETED)') AS value
FROM
generate_series(0, (SELECT max(id) FROM v)) AS s
LEFT JOIN
v
ON (s.value = v.id)
ORDER BY 1;
That will generate output that looks like this:
id value
-- ---------
0 (DELETED)
1 a
2 (DELETED)
3 (DELETED)
4 (DELETED)
5 e
6 f
7 (DELETED)
8 (DELETED)
9 (DELETED)
10 j
The table valued function generate_series()
should be in the shell, but may not be in the core library. See https://www.sqlite.org/series.html
(6) By anonymous on 2022-08-18 02:18:09 in reply to 3 [link] [source]
Thankyou
(4) By Ryan Smith (cuz) on 2022-08-18 01:43:11 in reply to 1 [link] [source]
And on the off chance you don't have a version with generate_series(), you can achieve the same using a CTE - like this example shamelessly plagiarising Jay's excellent example, but using the CTE in stead:
DROP TABLE IF EXISTS v;
CREATE TABLE v (
id INTEGER PRIMARY KEY NOT NULL,
value TEXT
);
INSERT INTO v VALUES
( 1, 'a')
,( 5, 'e')
,( 6, 'f')
,(10, 'j')
;
WITH GS(idx, maxid) AS (
SELECT 0, (SELECT max(id) FROM v)
UNION ALL
SELECT idx + 1, maxid FROM GS WHERE idx < maxid
)
SELECT GS.idx,
ifnull(v.value, '(DELETED)') AS value
FROM GS
LEFT JOIN v ON GS.idx = v.id
ORDER BY 1;
-- idx|value
-- ----|-----------
-- 0 |(DELETED)
-- 1 |a
-- 2 |(DELETED)
-- 3 |(DELETED)
-- 4 |(DELETED)
-- 5 |e
-- 6 |f
-- 7 |(DELETED)
-- 8 |(DELETED)
-- 9 |(DELETED)
-- 10 |j
(7) By anonymous on 2022-08-18 02:18:40 in reply to 4 [link] [source]
thankyou
(8) By anonymous on 2022-08-18 12:05:32 in reply to 4 [link] [source]
Hmmm I think maybe i've been misunderstood... this did indeed create the table that you show, but it was a completely new standalone table, unrelated to the data I am trying to query... So I am working on an iOS SMS.DB file... I would like to create a table using the existing data from the 'messages' table, but where there are missing ROWID numbers, I would like to have the messages table recreated with a line that is blank or with '(DELETED)' inserted and the rowid number recreated... SO my example: 81467 xxxxxxxxxx How’s the weather? 81468 xxxxxxxxxx Its good, its very sunny 81469 xxxxxxxxxx I like chocolate 81470 xxxxxxxxxx Same here, we should eat some because its sunny 81471 (DELETED) 81472 (DELETED) 81473 xxxxxxxxxx Sure why not! 81474 xxxxxxxxxx If we eat some maybe sqlite will be easier 81475 xxxxxxxxxx I refuse to let it beat us 81476 (DELETED) 81477 (DELETED) 81478 (DELETED) 81479 xxxxxxxxxx If sqlite ate chocolate it would be sqlfat32 81480 xxxxxxxxxx That’s awesome, you’re so funny 81481 (DELETED) 81482 xxxxxxxxxx Hahahaha I know, sometimes I just laugh myself to sleep But I want this to include the entire "message" table...
(9.1) By Ryan Smith (cuz) on 2022-08-18 12:58:18 edited from 9.0 in reply to 8 [source]
Apologies for not being more clear.
All of the solutions above offer an example of how your problem may be solved, not the actual SQL to solve it (since we don't know the actual schema). Even in the latest example above you show no field-names above your data, how must we know what they are?
You will need to rename the table references and fields to match your schema.
Or, if you post your schema (the CREATE TABLE statement at least) we're happy to translate that for you, but we are mostly engineers and programmers - mind-reading was not in the curriculum. :)