SELECT行没有重复和WHERE IN()

时间:2014-12-22 15:38:26

标签: sql postgresql

   SELECT formid, avals(data) as datavalues, akeys(data) as datakeys, taskid
      FROM task_form_data
      WHERE taskid IN (449750,449699,449620) 
      ORDER BY formid, timestamp DESC

将是一个测试查询 - 问题是表(我无法更改)的新行添加了新数据 - 但是formid保持不变。

因此,当我选择这样的时候,我也会得到旧的数据。 我不能使用DISTINCT ON(formid)。我需要最新的结果(通常3-4行与diff formid) - 对于每个taskid IN(来自php - 可以是大数字 - 不能对每个进行单独的查询)。 有没有办法让它像那样工作?

数据示例(只是一个简单的示例 - 较大的日期值将是最早的时间戳):

formid  timestamp  taskid
6       1          449750
2       2          449750  
2       3          449750
4       4          449750
4       5          449750

应该出现什么(各种形式的数量可以更大或更小):

6       1          449750
2       2          449750  
4       4          449750

更新:

SELECT DISTINCT ON(formid) formid, avals(data) as datavalues, akeys(data) as datakeys, taskid, timestamp
      FROM task_form_data
      WHERE taskid IN (450567,449699,449620)
      GROUP BY formid,taskid,data,timestamp
      ORDER BY formid,timestamp DESC

我尝试过 - 似乎工作 - 但只有taskid IN中的第一个参数。 是否可以修改它以使用数组中的每个值?

3 个答案:

答案 0 :(得分:1)

您可以使用row_number()执行此操作。例如,如果您想要最近的三行:

SELECT formid, avals(data) as datavalues, akeys(data) as datakeys, taskid
FROM (SELECT d.*, row_number() over (partition by formid, taskid order by timestamp desc) as seqnum
      FROM task_form_data d
      WHERE taskid IN (449750, 449699, 449620)
     ) d
WHERE seqnum <= 3
ORDER BY taskid, formid, timestamp DESC;

答案 1 :(得分:0)

我真的不喜欢这个,但如果你的桌子不大,它可以工作:

SELECT tfm.formid, tfm.avals(data) as datavalues, tfm.akeys(data) as datakeys, tfm.taskid
FROM task_form_data AS tfm
INNER JOIN
(
    SELECT formid, MAX(timestamp)
    FROM task_form_data
    WHERE taskid IN (449750,449699,449620)
    GROUP BY formid
) AS a
ON tfm.formid = a.formid
AND tfm.timestamp = a.timestamptimestamp
WHERE tfm.taskid IN (449750,449699,449620) 
ORDER BY tfm.formid, timestamp DESC;

你真的称之为“时间戳”字段吗?

答案 2 :(得分:0)

这符合您想要的输出。 SQL Fiddle

select *
from (
    select *,
        row_number() over(partition by taskid order by timestamp) as rn
    from (
        select distinct on (taskid, formid) *
        from task_form_data
        where taskid in (449750,449699,449620)
        order by taskid, formid, timestamp
    ) s
) s
where rn <= 3
order by taskid, timestamp

使用实时时间戳,必须在用于订购的任何地方添加desc,因为较新的时间戳大于较旧的时间戳。