2015-02-17 3 views
1

Я использую PostgreSQL и имеют следующие таблицы:Самый высокий для каждой группы, со счетом

 
users 
id name 
1 joe 
2 jack 
 
projects 
id name 
1 p1 
2 p2 
 
tasks 
id name user_id project_id due_on 
1 t1 1  1   2015-02-17 
2 t2 1  2   2015-02-18 
3 t3 2  1   2015-02-19 

Я хочу построить запрос, который возвращает строку для каждого пользователя, имеющего, по меньшей мере одно задание после 2012-01-01. Он должен указывать имя пользователя, количество задач пользователя, дату самой удаленной задачи и имя проекта, связанного с этой самой удаленной задачей.

С учетом указанными выше результатов таблицами должна быть

 
user_name max_due_on task_count project_name 
joe  2015-02-18 2   p2 
jack  2015-02-19 1   p1 

Я построить следующий запрос, но он отсутствует название проекта, связанное с дальними из-за задачами.

SELECT 
    users.name AS user_name, 
    max(tasks.due_on) AS max_due_on, 
    count(*) AS task_count 
FROM tasks 
LEFT JOIN users ON users.id = tasks.user_id 
LEFT JOIN projects ON projects.id = tasks.project_id 
WHERE 
    tasks.due_at > '2012-01-01' 
GROUP BY users.name 

Есть ли способ достичь того, что мне нужно?

EDIT: это является рабочим запросом, слегка адаптирован из Anwer Булата:

SELECT user_name, due_at, task_count, project_name 
    from (
     SELECT 
     users.name AS user_name, 
     projects.name AS project_name, 
     tasks.due_on, 
     count(*) OVER (PARTITION BY users.name) AS task_count, 
     row_number() over (PARTITION BY users.name ORDER BY tasks.due_on DESC) AS rn 
     FROM tasks 
     LEFT JOIN users ON users.id = tasks.user_id 
     LEFT JOIN projects ON projects.id = tasks.project_id 
     WHERE tasks.due_on > '2012-01-01' 
    ) t 
    WHERE rn = 1 
    ORDER by user_name 
+0

возможного дубликат [Лучшего в каждую группу] (HTTP: //stackoverflow.com/questions/28125273/highest-per-each-group) – Bulat

ответ

1

Вы должны попробовать что-то вроде этого:

 select user_name, due_on, task_count, project_name 
     from (
     SELECT 
      users.name, 
      projects.project_name, 
      tasks.due_on, 
      count(*) over (partition by user_name, project_name order by id desc) as AS task_count, 
      row_number() over (partition by user_name, project_name order by id desc) as rn 
      FROM tasks 
      LEFT JOIN users ON users.id = tasks.user_id 
      LEFT JOIN projects ON projects.id = tasks.project_id 
      WHERE 
      tasks.due_at > '2012-01-01' 
     ) t 
     where rn = 1 
     order by id; 
+0

Спасибо за ваш ответ; на самом деле я не хочу разбивать на 'projects.name', я хочу одну строку для каждого пользователя, независимо от количества проектов, с которыми связаны их задачи. Но мне все еще нужно, чтобы название проекта было связано с заданием максимальной даты на дату. – Florent2

+0

Спасибо, Булат, наконец, мог бы работать, благодаря вашему ответу. – Florent2

Смежные вопросы