I want to add records randomly in select result like this example:
1 a
2 a
- b
3 a
- b
4 a
5 a
6 a
- b
7 a
8 a
- b
In a simple query I select from a table but in this case I want result mix with b table without random a result otherwise I simply could union them and then order random().
EDIT:
-- ----------------------------
-- Table structure for t1
-- ----------------------------
DROP TABLE IF EXISTS `t1`;
CREATE TABLE `t1` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=11 DEFAULT CHARSET=utf8;
INSERT INTO `t1` VALUES ('1', 'a');
INSERT INTO `t1` VALUES ('2', 'a');
INSERT INTO `t1` VALUES ('3', 'a');
INSERT INTO `t1` VALUES ('4', 'a');
INSERT INTO `t1` VALUES ('5', 'a');
INSERT INTO `t1` VALUES ('6', 'a');
INSERT INTO `t1` VALUES ('7', 'a');
INSERT INTO `t1` VALUES ('8', 'a');
INSERT INTO `t1` VALUES ('9', 'a');
INSERT INTO `t1` VALUES ('10', 'a');
-- ----------------------------
-- Table structure for t2
-- ----------------------------
DROP TABLE IF EXISTS `t2`;
CREATE TABLE `t2` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8;
INSERT INTO `t2` VALUES ('1', 'b');
INSERT INTO `t2` VALUES ('2', 'b');
INSERT INTO `t2` VALUES ('3', 'b');
So I can union two tables and then order by random and the result will be like this:
SELECT
t1.ID,
t1.name
FROM
t1
UNION ALL
SELECT
t2.ID,
t2.name
FROM
t2
ORDER BY RAND();
5 a
2 a
6 a
3 a
7 a
2 b
9 a
1 a
10 a
3 b
4 a
8 a
1 b
But I don't want to random records I just only want mix two tables records like first example.
I hope my question is now clear.
I don't think pure SQL is the best solution here, I would do it in some end framework (I don't know what you use), like PHP, Delphi, Java, etc. This way is more easier and you can control it better. But if you would like to do it in SQL, here an idea:
SET #max_t1 = (SELECT MAX(ID) FROM t1);
SET #max_t2 = (SELECT MAX(ID) FROM t2);
SET #last_order = RAND()*#max_t1/#max_t2;
SELECT
t1.ID, t1.name, t1.ID AS "Ord"
FROM
t1
UNION ALL
SELECT
t2.ID, t2.name, #last_order:=#last_order+RAND()*#max_t1/#max_t2
FROM
t2
ORDER BY Ord
This way we generate a random position for TableB, then in every row we add some random value to it, in according to the size differency between the two tables, then order the whole result on this column.
Related
I have a source table (TableA) that contains multiple records for each day. I need to left join (on the date field) it to TableB that contains a few records per year.
The problem is that TableA should be joined to the earliest record from TableB where the date from TableA <= the date from TableB.
CREATE TABLE IF NOT EXISTS `tableA` (
`id` int(6) unsigned NOT NULL,
`date` date NOT NULL,
`content` varchar(200) NOT NULL,
PRIMARY KEY (`id`)
) DEFAULT CHARSET=utf8;
INSERT INTO `tableA` (`id`, `date`, `content`) VALUES
('1', '2017-10-03', 'The earth is round.'),
('2', '2018-01-01', 'The earth is flat'),
('3', '2018-01-01', 'One hundred angels can dance on the head of a pin'),
('4', '2018-01-02', 'The earth is flat and rests on a bull\'s horn'),
('5', '2018-01-03', 'The earth is like a ball.');
CREATE TABLE IF NOT EXISTS `tableB` (
`date` date NOT NULL,
`content` varchar(200) NOT NULL,
PRIMARY KEY (`date`)
) DEFAULT CHARSET=utf8;
INSERT INTO `tableB` (`date`, `content`) VALUES
('2017-01-01', 'ONE'),
('2017-12-01', 'TWO'),
('2018-01-02', 'THREE'),
('2018-01-05', 'FOUR');
Based on the this SQLFiddle, I'm looking for the following result.
tableA.id | tableB.content
--------------------------
1 | TWO
2 | THREE
3 | THREE
4 | THREE
5 | FOUR
Here is one solution:
SELECT a.id, b.content
FROM TableA a
JOIN TableB b ON b.date = (
SELECT MIN(b2.date)
FROM TableB b2
WHERE b2.date >= a.date
);
I'm not sure whether this is the most efficient way, but it works.
I have two table which I want to left join.
DROP TABLE IF EXISTS test_1;
CREATE TABLE test_1 (
id int(11) NOT NULL AUTO_INCREMENT,
name varchar(32) NOT NULL,
description varchar(255) NOT NULL,
PRIMARY KEY (id)
) ;
-- ----------------------------
-- Records of test_1
-- ----------------------------
INSERT INTO test_1 VALUES ('1', 'Item A', 'Description for Item A');
INSERT INTO test_1 VALUES ('2', 'Item B', 'Description for Item B');
INSERT INTO test_1 VALUES ('3', 'Item C', 'Description for Item C');
INSERT INTO test_1 VALUES ('4', 'Item D', 'Description for Item D');
INSERT INTO test_1 VALUES ('5', 'Item E', 'Description for Item E');
DROP TABLE IF EXISTS test_2;
CREATE TABLE test_2 (
id int(11) NOT NULL AUTO_INCREMENT,
ids varchar(32) NOT NULL,
PRIMARY KEY (id)
);
-- ----------------------------
-- Records of test_2
-- ----------------------------
INSERT INTO test_2 VALUES ('1', '1,2,5');
I want to return the same result that (A) will give but from (B)
(A) SELECT t1.*, t2.id as control FROM test_1 t1 LEFT JOIN test_2 t2 ON t1.id IN (1,2,5);
(B) SELECT t1.*, t2.id as control FROM test_1 t1 LEFT JOIN test_2 t2 ON t1.id IN (t2.ids)
The problem is that MySQL IN expects an array while I have a string from t2.ids column. Is there any way out?
Thanks to all that have contributed. Nevertheless, I was able to find my solution with MySQL FIND_IN_SET
SELECT t1.*, t2.id as control FROM test_1 t1 LEFT JOIN test_2 t2 ON t1.id= FIND_IN_SET(t1.id, t2.ids);
how can i count how many people in table a?
there 4 people exists in the below table , how can i get "4" in mysql?
SET FOREIGN_KEY_CHECKS=0;
-- ----------------------------
-- Table structure for `a`
-- ----------------------------
DROP TABLE IF EXISTS `a`;
CREATE TABLE `a` (
`products_id` int(11) NOT NULL auto_increment,
`name` varchar(30) default NULL,
`date` datetime default NULL,
PRIMARY KEY (`products_id`)
) ENGINE=MyISAM AUTO_INCREMENT=8 DEFAULT CHARSET=utf8;
-- ----------------------------
-- Records of a
-- ----------------------------
INSERT INTO `a` VALUES ('1', 'jimmy', '2014-02-11 09:24:42');
INSERT INTO `a` VALUES ('7', 'khon', '2014-02-19 09:24:50');
INSERT INTO `a` VALUES ('3', 'jimmy', '2014-01-11 09:25:03');
INSERT INTO `a` VALUES ('4', 'kelvin', '2013-12-11 09:25:09');
INSERT INTO `a` VALUES ('5', 'ricky', '2014-02-12 09:25:14');
Use count on distinct name of the persons.
select count(distinct name) from a mytable
select count(distinct(name)) as count from a;
You can use COUNT LIke
SELECT COUNT(DISTINCT name) FROM a;
You are unclear in your question. What is it that you want to count?, number of distinct persons or the total number of people in the table?
SELECT COUNT(name) from a;
You may use DISTINCT clause with it or you can also perform GROUP BY to get the count of users by grouping them.
I wish to know which team in "TX" have not played a game. (In other words Im looking for a selection of records where there is no related record in the many table.)
Here is the SQL:
(Or if You prefer the sql fiddle is here:http://sqlfiddle.com/#!2/14106 )
CREATE TABLE `Team` (
`ID` INT NOT NULL AUTO_INCREMENT ,
`Name` VARCHAR(45) NULL ,
`State` VARCHAR(45) NULL ,
PRIMARY KEY (`ID`) );
CREATE TABLE `Games` (
`ID` INT NOT NULL AUTO_INCREMENT,
`Team_ID` INT NULL ,
`Game_Day` DATE NULL ,
PRIMARY KEY (`ID`) );
INSERT INTO `Team` (`Name`, `State`) VALUES ('Rams', 'TX');
INSERT INTO `Team` (`Name`, `State`) VALUES ('Rockets', 'OK');
INSERT INTO `Team` (`Name`, `State`) VALUES ('Bombers', 'TX');
INSERT INTO `Team` (`Name`, `State`) VALUES ('Yellow Jackets', 'NV');
INSERT INTO `Team` (`Name`, `State`) VALUES ('Wildcats', 'CT');
INSERT INTO `Team` (`Name`, `State`) VALUES ('Miners', 'CO');
INSERT INTO `Team` (`Name`, `State`) VALUES ('Bolts', 'TX');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('2', '2013-03-16');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('2', '2013-01-01');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('3', '2013-04-16');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('5', '2013-02-02');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('4', '2013-02-12');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('6', '2013-01-09');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('6', '2013-01-01');
INSERT INTO `Games` (`Team_ID`, `Game_Day`) VALUES ('3', '2013-05-01');
I should get the result:
ID Name
1 Rams
7 Bolts
SELECT `ID`, `Name` FROM `TEAM`
WHERE `ID` NOT IN (SELECT DISTINCT(`Team_ID`) from `Games`)
AND `State` = 'TX';
SqlFiddle here.
Use an outer join, selecting only those rows that don't match
SELECT t.*
FROM TEAM t
LEFT JOIN GAMES g ON g.team_id = t.id
WHERE t.state = 'TX'
AND g.team_id is null -- return only rows that *don't* join
This this running in SQL Fiddle
Note that using a join will out-perform a sub-query approach, especially when data sets become large.
You can also left-join to the Games table and filter for where there isn't a corresponding Games row. This is usually faster than NOT IN when the tables have a lot of rows:
SELECT Team.ID, Team.Name
FROM Team
LEFT JOIN Games ON Team.ID = Games.Team_ID
WHERE Team.State = 'TX' AND Games.ID IS NULL;
If there isn't a Games row to go with the Teams row, the Games.ID column will be null in the result, so if you filter on Games.ID IS NULL you'll get all the rows where a team has no games.
There's a SQL Fiddle here.
Hope this would help.
select t.ID,t.NAME
FROM Team t
WHERE t.state = 'TX'
AND t.id NOT IN (SELECT g.TEAM_ID FROM Games g)
I have two tables as shown below.
table1
site | Link type
-----+----------
A | pdf
B | html
C | NULL
D | NULL
Table2
site | link type
-----+----------
C | htm
D | doc
This is the result I want:
site | link type
-----+----------
A | pdf
B | html
C | htm
D | doc
I want an insert query to insert the values of link type from table 2 to table 1
where link type is null joined with the condition with of table1.site = table2.site.
I tried:
INSERT INTO table1(linktype)
SELECT linktype FROM table1 t1
JOIN table2 t2
ON t1.site=t2.site
I want a insert query. as update query is working and want to know how a insert can be done?
Edit: Completely edited after clarification:
Creation of table1:
SET FOREIGN_KEY_CHECKS=0;
DROP TABLE IF EXISTS `table1`;
CREATE TABLE `table1` (
`site` varchar(250) DEFAULT NULL,
`linktype` varchar(250) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
INSERT INTO `table1` VALUES ('A', 'pdf');
INSERT INTO `table1` VALUES ('B', 'html');
INSERT INTO `table1` VALUES ('C', null);
INSERT INTO `table1` VALUES ('D', null);
Creation of table2:
SET FOREIGN_KEY_CHECKS=0;
DROP TABLE IF EXISTS `table2`;
CREATE TABLE `table2` (
`site` varchar(250) DEFAULT NULL,
`linktype` varchar(250) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
INSERT INTO `table2` VALUES ('C', 'htm');
INSERT INTO `table2` VALUES ('D', 'doc');
Insert query:
INSERT INTO
table1
(site, linktype)
(
SELECT
table2.site,
table2.linktype
FROM
table2
JOIN
table1
ON
table1.site = table2.site
)
;
Table1 after insert query: