在PostgreSQL中创建高效查询并合并语句

时间:2016-05-25 22:34:35

标签: sql postgresql

如果这是微不足道的,请原谅我 - 我是使用PostGRESQL的新手。我有两个 表:

CREATE TABLE group_users (
  user_id int NOT NULL PRIMARY KEY,
  group_id int NOT NULL,
  join_time timestamp NOT NULL,
  member_rank enum('l','a','m') DEFAULT NULL
);

CREATE TABLE interactions (
  interactionid int PRIMARY KEY NOT NULL,
  user_id int NOT NULL,
  target_user_id int NOT NULL,
  start_time timestamp NOT NULL
);

我现在必须回答这个问题:

不同群组中的用户之间的互动百分比是多少, 组中的用户与不在任何组中的用户以及相同的用户 组?

这是我的查询 - 但是,我必须将其合并为一个查询。

我的问题 是:

  1. 对于下面的查询,在PostGRESQL中有更有效的方法吗?

  2. 进行此一次查询的最有效方法是什么?

  3. - 使用交互信息将user_ids映射到group_ids

    CREATE TEMPORARY TABLE group_interaction_information AS
    SELECT 
    a.interactionid,
    a.user_id, 
    b.group_id, 
    a.target_user_id, 
    c.group_id AS target_group_id
    FROM interactions a
    LEFT JOIN
    group_users b
    on a.user_id = b.user_id
    LEFT JOIN
    group_users c
    ON a.target_user_id = c.user_id;
    

    - 差异组中用户互动的百分比

    select 
    (select count(*) from group_interaction_information
    where group_id != target_group_id and group_id is not null 
    and target_group_id is not null)/(select count(*) from group_interaction_information)::float;
    

    - 群组中用户的互动百分比

    select 
    (select count(*) from group_interaction_information
    where group_id is not null)/
    (select count(*) from group_interaction_information)::float;
    

    - 不在群组中的用户的互动百分比

    select
    (select count(*) from group_interaction_information where group_id is null)/
    (select count(*) from group_interaction_information)::float;
    

    - 来自同一组中用户的互动百分比

    select 
    (select count(*) from group_interaction_information
    where group_id = target_group_id and group_id is not null 
    and target_group_id is not null)/(select count(*) from group_interaction_information)::float;
    

1 个答案:

答案 0 :(得分:1)

组合查询的一种方法是使用条件聚合:

select 
    count(case when group_id <> target_group_id then 1 end) / count(*)::float,
    count(case when group_id is not null then 1 end) / count(*)::float,
    count(case when group_id is null then 1 end) / count(*)::float,
    count(case when group_id = target_group_id then 1 end) / count(*)::float
from group_interaction_information

顺便说一下,如果其中一列或两列都为空,a = b将永远不会为真,因此如果您的条件为group_id = target_group_id,则无需指定and target_group_id is not null。这同样适用于a <> b。要测试投放select null = null, null <> null, 'a' <> null - 这些都会产生null

相关问题