简体   繁体   English

如何删除子查询?

[英]How can I remove the subquery?

In PostgreSQL database I have such table with information about relationship between organizations.PostgreSQL数据库中,我有这样的表,其中包含有关组织之间关系的信息。 As you can see each organization has their own parent.如您所见,每个组织都有自己的父级。

| organization_id | organization_name | organization_rang | parent_organization_id |
| ----------------|-------------------|-------------------|------------------------|
| 1               | Alphabet          | 1                 |                        |
| 2               | Google            | 2                 | 1                      |
| 3               | X Development     | 3                 | 2                      |
| 4               | Apple             | 1                 |                        |

I am trying to create sql query which will return new column.我正在尝试创建 sql 查询,该查询将返回新列。 If organization has child I need to set true to that new column, otherwise I need to set false.如果组织有孩子,我需要为该新列设置 true,否则我需要设置 false。 Other word I need such result:换句话说,我需要这样的结果:

| organization_id | organization_name | organization_rang | parent_organization_id | has_child |
| ----------------|-------------------|-------------------|------------------------|-----------|
| 1               | Alphabet          | 1                 |                        | true      |
| 2               | Google            | 2                 | 1                      | true      |
| 3               | X Development     | 3                 | 2                      | false     |
| 4               | Apple             | 1                 |                        | false     |

I used next code which works, but in my opinion this is not the best solution to make a subquery on the same table.我使用了下一个有效的代码,但我认为这不是在同一个表上进行子查询的最佳解决方案。 How can I improve the code and speed up the query in your opinion?您认为如何改进代码并加快查询速度?

SELECT
    A.*,
    CASE
        WHEN EXISTS(
            SELECT *
            FROM HISTORY
            WHERE PARENT_ORGANIZATION_ID = A.ORGANIZATION_ID
        ) THEN TRUE
        ELSE FALSE
    END HAS_CHILD   
FROM HISTORY AS A

You can use conditional ( case..when ) statement:您可以使用条件( case..when )语句:

SELECT A.*, 
       (CASE
           WHEN PARENT_ORGANIZATION_ID = A.ORGANIZATION_ID
           THEN 'true'
           ELSE 'false'
       END) AS HAS_CHILD
  FROM HISTORY AS A;

I quoted true and false because of the desired results are not boolean but of string type.我引用false true ,因为所需的结果不是 boolean 而是字符串类型。

As @a_horse_with_no_name commented, there is no need for the case expression;正如@a_horse_with_no_name 评论的那样,不需要case表达式; EXISTS(...) already yields a boolean value: EXISTS(...)已经产生了 boolean 值:


SELECT a.*
    , EXISTS( SELECT * FROM history x
            WHERE x.parent_organization_id = a.organization_id
        ) AS has_child 
FROM history a
        ;

LEFT JOIN version: LEFT JOIN版本:

SELECT
    A.*,
    B.PARENT_ORGANIZATION_ID is not null HAS_CHILD   
FROM
    HISTORY AS A
LEFT JOIN (select distinct PARENT_ORGANIZATION_ID from HISTORY) as B
    on B.PARENT_ORGANIZATION_ID = A.ORGANIZATION_ID

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM