选择以连接查询中的给定部分结尾的行?

时间:2012-04-29 08:38:24

标签: sql sqlite select subquery

我正在尝试创建一个复杂的SQL查询(至少对我而言),但实际上不知道从哪里开始。

基本上,我有一个角色对象,每个角色可以由几个部分组成。例如:

字符表:

id | character
--------------
1  | 你
2  | 是
3  | 有

character_parts 表格:

id | character_id | part_id
---------------------------
1  | 1            | 4
2  | 1            | 9
3  | 1            | 5
4  | 2            | 2
5  | 2            | 34
6  | 2            | 43
7  | 3            | 21
8  | 3            | 16
9  | 3            | 41
10 | 3            | 43

因此,我知道:

Character 1 is made of parts 4, 9, 5
Character 2 is made of parts 2, 34, 43
Character 3 is made of parts 21, 16, 41, 43

现在我要做的是选择指定部分结束的所有字符。

例如,如果我选择以“16,41,43”结尾的所有字符,我将获得字符3.如果我选择以“43”结尾的所有字符,我将获得字符3和4。

我假设我需要使用子查询构建一些查询,但不确定如何启动,或者是否可以完成。到目前为止,我只是选择包含所需部件ID的所有内容,然后以编程方式进行比较,但这太慢了,因为我选择的方式超出了需要。

有什么建议吗?

4 个答案:

答案 0 :(得分:0)

查询可能是这样的。

select * from character where id in (select character_id from character_parts where character_id = 'required no' AND character_id = 'required no' AND character_id = 'required no')
//required number is the part_id you want to specify.

答案 1 :(得分:0)

添加另一列from_end,从最后开始计算,说:

from_end | id | character_id | part_id
--------------------------------------
      2  | 1  | 1            | 4
      1  | 2  | 1            | 9
      0  | 3  | 1            | 5
      2  | 4  | 2            | 2
      1  | 5  | 2            | 34
      0  | 6  | 2            | 43
      3  | 7  | 3            | 21
      2  | 8  | 3            | 16
      1  | 9  | 3            | 41
      0  | 10 | 3            | 43

然后你可以这样做:

SELECT p0.character_id
  FROM character_parts AS p0
  JOIN character_parts AS p1 USING (character_id)
  JOIN character_parts AS p2 USING (character_id)
 WHERE p0.from_end = 0 AND p1.from_end = 1 AND p2.from_end = 2
   AND p0.part_id = 43 AND p1.part_id = 41 AND p2.part_id = 16

答案 2 :(得分:0)

您可以尝试group_concat功能: http://www.sqlite.org/lang_aggfunc.html

SELECT group_concat(part_id) FROM character_parts WHERE character_id=1

查询应返回4,9,5

问题是group_concat使用的顺序是任意的:

Sqlite group_concat ordering

因此,假设您有一个字段position来定义部件的顺序,我们可以像这样更新查询:

SELECT group_concat(part_id) FROM (SELECT part_id FROM character_parts WHERE character_id=1 ORDER BY position ASC)

查询现在将完全按照定义的顺序返回4,9,5部分。

现在我们有了这个值,我们可以像常规字符串一样进行搜索。 如果我们想要找到以某个字符串结尾的所有值,我们可以使用LIKE运算符。

最后,查询会像这样:

SELECT character_id, parts_concat FROM (
    SELECT character_id, group_concat(part_id) FROM (
        SELECT character_id, part_id FROM character_parts WHERE ORDER BY position ASC
    ) GROUP BY character_id
) parts
WHERE parts_concat LIKE '%,9,5'

答案 3 :(得分:0)

SELECT  c.character
FROM    character_parts cp
JOIN    character c
ON      c.id = cp.character_id
WHERE   cp.part_id = 43
        AND cp.id =
        (
        SELECT  id
        FROM    character_parts cpo
        WHERE   cpo.character_id = cp.character_id
        ORDER BY
                id DESC
        )

创建以下索引:

character_parts (part_id, character_id, id)
character_parts (character_id, id)

让它快速工作