2017-11-11 121 views
1

我不擅长sql,但我到了那里。我搜索了stackoverflow,但我似乎无法找到解决方案,我希望有人能帮助我。我有一个表(用户)与数据如下。 book_id列是另一张包含用户订阅的书籍的关键字。如何在同一个表上合并两个查询以获得MySQL中的单个结果集

|--------|---------------------|------------------| 
| id |  book_id  |  name  | 
|--------|---------------------|------------------| 
| 1 |   1   |  jim  | 
| 2 |   1   |  joyce  | 
| 3 |   1   |  mike  | 
| 4 |   1   |  eleven  | 
| 5 |   2   |  max  | 
| 6 |   2   |  dustin  | 
| 7 |   2   |  lucas  | 
|--------|---------------------|------------------| 

我在我的PHP代码中有一个函数,它返回来自特定书籍ID(1或2)的两个随机用户。查询中的一个返回结果在第1列,并导致2返回在柱状2的结果:

|---------------------|------------------| 
|   1   |  2   | 
|---------------------|------------------| 
|  jim   |  max  | 
|  joyce   |  dustin  | 
|---------------------|------------------| 

我已经通过运行两个单独的查询,如下所示来实现这一点。我想知道是否有可能通过一个查询以及如何实现此功能。

$random_users_with_book_id_1 = SELECT name FROM users WHERE book_id=1 LIMIT 2 
$random_users_with_book_id_2 = SELECT name FROM users WHERE book_id=2 LIMIT 2 

再一次,我很抱歉,如果它太具体。下面的查询已经最接近我试图实现的。:

SELECT a.name AS book_id_1, b.name AS book_id_2 
FROM users a, users b 
WHERE a.book_id=1 AND b.book_id = 2 
LIMIT 2 

编辑:我创造了一个小提琴与他一起玩。我感谢任何帮助!谢谢!! http://sqlfiddle.com/#!9/7fcbca/1

+0

你不清楚。请尽力解释结果如何作为输入的函数。你似乎想要将两列并排配对。 (可能只是在DBMS之外更好地完成用户gui格式化。)将行号列添加到table1的受限排序限制,加入行号相等,然后选择其他列。这*是一个常见问题 - 谷歌更多,直到你找到答案或部分答案 - 你不是第一个问这个问题的人。注意:MySQL没有ROW_NUMBER或RANK,并且在一个SELECT语句* undefined *中读取和更新变量。 – philipxy

+0

谢谢@philipxy。我同意,我需要更多地解释这一点,并且我编辑了我的问题,并且包含了一个小提琴。我在我的PHP代码中有一个函数,它需要一个具有1和2作为n_id的用户列表。在我的PHP代码中,我调用了两个不同的sql函数,一个从n_id 1获取用户,另一个从n_id 2获取用户。我认为使用一个sql查询获得两组用户的方法更好。那可能吗?我在这里错过了什么吗?再次,我不擅长SQL。我将继续搜索SO和Google。我敢肯定,答案是在那里 – realnsleo

+0

PS谷歌搜索'stackoverflow“mysql”把两列并排按行号“给https://stackoverflow.com/q/40482804/3404097及其他人,但他们使用@ n = @的n + 1。在MySQL中,为了获得行号,你必须编写一个程序,通过循环插入增加列号。 (你可以单独谷歌。)MySQL的公司Percona已经表明,MySQL的当前代码可以使用CASE以某种方式安全地使用@ n = @ n + 1,但是我现在没有链接。不停寻找。 – philipxy

回答

1

这是很容易实际上:)

你可以使用UNION这样的:

SELECT * FROM (
    (SELECT * FROM user WHERE n_id=1 LIMIT 2) 
    UNION 
    (SELECT * FROM user WHERE n_id=2 LIMIT 2)) 
collection; 

如果你读这篇文章关于the documentation你可以使用()来组各个查询和应用中间的联盟。没有括号,它仍然会限制2,只显示两个。参考。 “通过或LIMIT应用于为了将个人选择,将子句封闭SELECT括号内:”

+0

像包含文档的魅力和+1一样工作。它帮助了很多。只有一个问题,是“收集”意味着什么?我注意到没有它的查询不起作用。而且我注意到我可以将其更改为任何内容并且查询起作用。我猜这应该是一个别名? – realnsleo

+0

谢谢。没有收集只是我选择的名称,使用任何你喜欢的东西。是的,你需要这样做才能将联盟结果分组; – oetoni

1

如果你想在MySQL查询相结合,你可以用括号:

(SELECT name 
FROM users 
WHERE n_id = 1 
LIMIT 2 
) UNION ALL 
(SELECT name 
FROM users 
WHERE n_id = 2 
LIMIT 2 
); 

首先,如果您特别想要承担删除重复项的开销,请仅使用UNION。否则,请使用UNION ALL

二,此行不返回随机行。这返回任意行。在很多情况下,这可能是数据开始附近的两行。如果你想随机行中,然后使用ORDER BY rand()

(SELECT name 
FROM users 
WHERE n_id = 1 
ORDER by rand() 
LIMIT 2 
) UNION ALL 
(SELECT name 
FROM users 
WHERE n_id = 2 
ORDER BY rand() 
LIMIT 2 
); 

还有其他的方法,这些方法更有效,但是这应该是罚款高达几千行。

+0

太棒了!这很有帮助。并感谢区分'UNION'和'UNION ALL'。如果你不介意,你能解释一下你的意思吗?谢谢。 – realnsleo

+1

@realnsleo。 。 。 'UNION'比'UNION ALL'慢。 –

相关问题