Say I have the following 2 tables,
CREATE TABLE t1(
name VARCHAR(25) NOT NULL,
time INT,
a INT
);
CREATE TABLE t2(
name VARCHAR(25) NOT NULL,
time INT,
b INT
);
and Im looking to pull all the values (a) out of t1 with a given time, all the values with the previous time (say just time-1 for convenience) then for each name subtract the newer one from the older one and insert those values into t2 with the same time. The slow way of doing this would involve doing something like
SELECT name, a FROM t1 WHERE time = x;
SELECT name, a FROM t1 WHERE time = x-1;
(subtract the as for each name)
INSERT INTO t2 VALUES ....;
From my (limited) understanding of subqueries, there should hopefully be a way to do this all in 1 query. Any ideas? Thanks in advance :)
It looks like you can use the INSERT ... SELECT syntax:
INSERT INTO t2 (name, time, b)
SELECT ta.name, ta.time time, (ta.a - tb.a) b
FROM t1 ta
JOIN t1 tb ON (tb.time = ta.time - 1 AND tb.name = ta.name);
Test case:
INSERT INTO t1 VALUES ('t1', 1, 100);
INSERT INTO t1 VALUES ('t1', 2, 200);
INSERT INTO t1 VALUES ('t1', 3, 500);
INSERT INTO t1 VALUES ('t1', 4, 600);
INSERT INTO t1 VALUES ('t1', 5, 800);
INSERT INTO t1 VALUES ('t1', 6, 900);
Result:
SELECT * FROM t2;
+------+------+------+
| name | time | b |
+------+------+------+
| t1 | 2 | 100 |
| t1 | 3 | 300 |
| t1 | 4 | 100 |
| t1 | 5 | 200 |
| t1 | 6 | 100 |
+------+------+------+
5 rows in set (0.00 sec)
there is im mysql insert ... select
INSERT INTO table ( fields )
SELECT fields FROM table;
Related
I know there are a number of questions here relating to what I am facing, but none of them are able to solve my situation.
I have two tables TABLE_1 and TABLE_2.
Table TABLE_1 has columns:
ID,
NAME
Table TABLE_2 has columns:
CODE,
AMOUNT,
QUANTITY
The two tables have a different number of columns but the row count is same.
Is possible to write an SQL query wherein I can retrieve all the columns from both the table in a single result set.
I am working on MySQL server.
Note: Both the tables have no common column. Any help is appreciated.
This is how I wish to retrieve:
| ID | NAME | CODE | AMOUNT | QUANTITY |
| | | | | |
| | | | | |
| | | | | |
Refer below query
SELECT a.ID, a.NAME, b.CODE,b.AMOUNT ,b.QUANTITY
FROM (SELECT
ROW_NUMBER() OVER(ORDER BY name ASC) AS RowNo, * FROM TABLE_1 )a
inner join (SELECT
ROW_NUMBER() OVER(ORDER BY CODE ASC) AS RowNo, * FROM TABLE_2 )b
On a.RowNo= b.RowNo
#Allan, here is my solution. Hope it helps.
CREATE TABLE t1(
ID INTEGER,
NAME VARCHAR(10)
);
CREATE TABLE t2(
CODE INTEGER,
AMOUNT INTEGER,
QUANTITY INTEGER
);
INSERT INTO t1 VALUES(91, 'Name1');
INSERT INTO t1 VALUES(92, 'Name2');
INSERT INTO t1 VALUES(93, 'Name3');
INSERT INTO t2 VALUES(1, 123, 2);
INSERT INTO t2 VALUES(2, 233, 4);
INSERT INTO t2 VALUES(3, 433, 1);
Query:
SET #rank=0;
SET #rank2=0;
select id,name,code,amount,quantity
from
(SELECT #rank:=#rank+1 AS rank, id, name
from t1) a,
(SELECT #rank2:=#rank2+1 AS rank, code, amount, quantity
from t2) b
where a.rank=b.rank;
I have following 2 tables t1, t2
CREATE TABLE t1 (
id INT PRIMARY KEY
);
CREATE TABLE t2 (
id INT PRIMARY KEY
);
INSERT INTO t1 VALUES (1),(2),(3);
INSERT INTO t2 VALUES (2),(3),(4);
I am running
select * from t1 left join t2 using(id);
Result:
+----+
| id |
+----+
| 1 |
| 2 |
| 3 |
+----+
On running script:
select t1.id, t2.id from t1 left join t2 using(id);
Result:
+----+------+
| id | id |
+----+------+
| 1 | NULL |
| 2 | 2 |
| 3 | 3 |
+----+------+
select * is supposed to return all the columns, so, why I am not getting 2 rows when I am using select *?
Note: I am using Mysql
as doc says:
Natural joins and joins with USING, including outer join variants, are processed according to the SQL:2003 standard:
Redundant columns of a NATURAL join do not appear. Consider this set of statements:
CREATE TABLE t1 (i INT, j INT);
CREATE TABLE t2 (k INT, j INT);
INSERT INTO t1 VALUES(1, 1);
INSERT INTO t2 VALUES(1, 1);
SELECT * FROM t1 JOIN t2 USING (j);
column j is named in the USING clause and should appear only once in the output, not twice.
This is the normal behavior of the USING clause. Here's a quote from MySQL documentation:
Similarly, in the second SELECT statement, column j is named in the USING clause and should appear only once in the output, not twice.
(JOIN syntax)
And here's from Wikipedia:
[...] any columns mentioned in the USING list will appear only once, with an unqualified name, rather than once for each table in the join.
(JOIN (SQL)
I have two tables (t1 & t2):
t1 (second column is array)
name | code
ee | 123, 124, 125
ef | 121, 123
______________________
t2
code_id | code_desc
121 | xxxxx
123 | yyyyyyy
124 | xxxxxxxx
if I do this query, all is ok:
SELECT * FROM t2 where code_id in (121,122)
but if I do this query I got NULL cell / result
SELECT * FROM t2 where code_id in (SELECT code FROM t1 where name = ee)
How can I get from one query all the info from two table?
Here is the code, I cant find a good sql online tool
CREATE TABLE t1 (name VARCHAR(200), codes VARCHAR(200));
CREATE TABLE t2 (codes_id VARCHAR(200), codes_desc VARCHAR(200));
INSERT INTO t1 (name, codes) VALUES ('ee', '123,124,125');
INSERT INTO t1 (name, codes) VALUES ('ef', '121,124');
INSERT INTO t1 (name, codes) VALUES ('eh', '123,124,125');
INSERT INTO t2 (codes_id, codes_desc) VALUES ('121', 'yyyyyyyyy');
INSERT INTO t2 (codes_id, codes_desc) VALUES ('122', 'xxxxxxxxx');
INSERT INTO t2 (codes_id, codes_desc) VALUES ('123', 'zzzzzzzzzzz');
SELECT * FROM t2 where code_id in (121,122)
SELECT * FROM t2 where code_id in (SELECT codes FROM t1 where name = 'ee')
You can use find_in_set function:
select *
from t2
where exists (
select 1
from t1
where name = 'ee'
and find_in_set(t2.code_id, t1.code) > 0
)
I'll advise you to normalize your table structure though. Because even though the above query is working, it is non-sargable.
There are 2 tables
table1 table2
book_id | tag_id tag_id
---------------- -----------
5 | 1 1
5 | 3 3
5 | 4 4
7 | 1
7 | 2
7 | 4
I need to create sql query for selection all book_id where tag_id is multitude of all tag_id from table2 (SQLite).
For example, book_id = 5 is acceptable because it has all tags from table2 (1, 3, 4).
The book with book_id = 7 isn't acceptable because it has only 1 and 4 tags, but hasn't tag_id = 3.
I'm not sure if this query will be very efficient, but...
select distinct book_id from table1 x
where not exists(
select * from table2 t where not exists(
select * from table1 a
where a.tag_id = t.tag_id
and a.book_id = x.book_id));
Setup code:
drop table table1;
drop table table2;
create table table1(book_id int, tag_id int);
insert into table1 values(5, 1);
insert into table1 values(5, 3);
insert into table1 values(5, 4);
insert into table1 values(7, 1);
insert into table1 values(7, 2);
insert into table1 values(7, 4);
create table table2(tag_id int);
insert into table2 values(1);
insert into table2 values(3);
insert into table2 values(4);
Is there a way to if else tables in mysql?
Example:
select * from tableA A, if(tableA.find=1,TableBA B,TableBB B) where A.id = B.aid
Real Example:
tables are: location_order, order_contract, order_gm, order_gm_hh:
select *
from location order lo, order_contract oc, if(lo.hh=0,order_gm,order_gm_hh) as og
where lo.orderid = oc.orderid && oc.gmid = og.id
You can left outer join both tables, and then use the IF() function in the SELECT clause:
SELECT a.*,
IF(a.find = 1, b1.value, b2.value) b_value
FROM tableA a
LEFT JOIN tableBA b1 ON (b1.aid = a.id)
LEFT JOIN tableBB b2 ON (b2.aid = a.id);
Test case:
CREATE TABLE tableA (id int, find int, value int);
CREATE TABLE tableBA (id int, aid int, value int);
CREATE TABLE tableBB (id int, aid int, value int);
INSERT INTO tableA VALUES (1, 1, 100);
INSERT INTO tableA VALUES (2, 0, 200);
INSERT INTO tableA VALUES (3, 1, 300);
INSERT INTO tableA VALUES (4, 0, 400);
INSERT INTO tableBA VALUES (1, 1, 10);
INSERT INTO tableBA VALUES (2, 3, 20);
INSERT INTO tableBB VALUES (1, 2, 30);
INSERT INTO tableBB VALUES (2, 4, 40);
Result:
+------+------+-------+---------+
| id | find | value | b_value |
+------+------+-------+---------+
| 1 | 0 | 100 | 10 |
| 2 | 1 | 200 | 30 |
| 3 | 0 | 300 | 20 |
| 4 | 1 | 400 | 40 |
+------+------+-------+---------+
4 rows in set (0.00 sec)
Do an outer join on both tables and use a case statement in the select to pull the value from whichever table meets the Find=1 criteria using a case statement.
SELECT Case A.Find
WHEN 1 THEN B1.SomeField
ELSE B2.SomeField
END as SomeField
FROM tableA A
LEFT JOIN tableBA b1 ON (b1.aid = A.id)
LEFT JOIN tableBB b2 ON (b2.aid = A.id);
You could have to separate this out into two select statements. For example:
select * from tableA A
inner join TableBA B on A.id = B.aid
where A.find = 1
UNION
select * from tableA A
inner join TableBB B on A.id = B.aid
where A.find <> 1