当前位置: 首页 > 面试题库 >

在SELECT中过滤出重复的后续记录

贺俊楚
2023-03-14
问题内容

(PostgreSQL 8.4) 表“
trackingMessages”存储移动设备(tm_nl_mobileid)和固定设备(tm_nl_fixedId)之间的跟踪事件。

CREATE TABLE trackingMessages
(
  tm_id SERIAL PRIMARY KEY,           -- PK
  tm_nl_mobileId INTEGER,             -- FK to mobile
  tm_nl_fixedId INTEGER,              -- FK to fixed
  tm_date INTEGER,                    -- Network time
  tm_messageType INTEGER,             -- 0=disconnect, 1=connect
  CONSTRAINT tm_unique_row
    UNIQUE (tm_nl_mobileId, tm_nl_fixedId, tm_date, tm_messageType)
);

这里的问题是,同一台移动设备随后可能会连接到同一固定设备两次(或多次)。我不希望看到后续的固定装置,但是如果以后有连接到另一个固定装置的移动设备,可以稍后再将其连接到相同的固定装置。

我想我很亲密,但还不完全。我一直在使用以下CTE(可在Stack Overflow上找到)

WITH cte AS 
(
  SELECT tm_nl_fixedid, tm_date, Row_number() OVER (
    partition BY tm_nl_fixedid
    ORDER BY tm_date ASC
  ) RN 
  FROM   trackingMessages
) 
SELECT * FROM cte 
  WHERE tm_nl_mobileid = 150 AND tm_messagetype = 1
  ORDER BY tm_date;

给我以下结果

32;1316538756;1
21;1316539069;1
32;1316539194;2
32;1316539221;3
21;1316539235;2

这里的问题是最后一列应为1、1、1、2、1,因为第三个“ 32”实际上是重复的跟踪事件(同一固定位置连续两次),并且最后一个连接到“
21”可以,因为介于两者之间。

请不要建议使用游标,
这是我目前正在努力摆脱的目标。游标解决方案确实有效,但是考虑到我必须处理的记录量,它太慢了。我宁愿修复CTE,也只选择位置RN = 1…,除非您有更好的主意!


问题答案:

好吧,您并不是那么亲密,因为row_number()无法同时跟踪两组的序列。PARTITION BY tm_nl_fixedid ORDER BY date RESTART ON GAP不存在,没有这样的东西。

Itzik Ben-
Gan为您面临的孤岛和缝隙问题提供了一种解决方案(实际上是几种解决方案)。想法是按主要条件(日期)对行进行排序,然后按划分条件+主要条件对行进行排序。序号之间的差异将保持不变,因为它们属于相同的分区标准和日期系列。

with cte as
(
  select *,
      -- While order by date and order by something-else, date
      -- run along, they belong to the same sequence
         row_number() over (order by tm_date)
       - row_number() over (order by tm_nl_fixedid, tm_date) grp
    from trackingMessages
)
select *,
    -- Now we can get ordinal number grouped by each sequence
       row_number() over (partition by tm_nl_fixedid, grp
                          order by tm_date) rn
  from cte
 order by tm_date

这是带有示例的Sql Fiddle。

这是Sql Server MVP Deep
Divs的第5章,其中提供了一些解决孤岛和空白问题的方法。



 类似资料:
  • 在Java8中使用和我是新手。我目前正在使用库来实现一些ML算法。我有以下代码: 如果数据正确或为空,函数将返回一个新的。如何在之后过滤(删除)对象?

  • 问题内容: 我正在运行一个简单的JSON文件,并希望获取类别名称。大约有100个对象,每个对象都属于一个类别-但是只有大约6个类别。 我当前的代码是这样的: 输出是100个不同的选项,大部分重复。我该如何使用Angular来检查a是否已经存在,如果已经存在则不创建选项? 编辑:在我的javascript中,只是为了澄清 问题答案: 您可以使用AngularUI 的 唯一 过滤器(此处提供源代码:A

  • 问题内容: 编辑:当我说“ SQL Server”时,我实际上是在谈论Management Studio。 抱歉,这令人困惑。 哦,我讨厌这种事情发生。昨天我在使用SQL Server,并尝试使用PIVOT命令来弄清楚它是如何工作的。因此,我创建了一个包含四列的新表,第一列的前几行将具有相同的值。 我在第一行,第一列中添加了“ value1”,然后按回车键–因为还没有添加任何键或约束,它使我可以向

  • null temp_location=pcoll.pipeline.options.view_as(Traceback(最近的调用最后):文件“run.py”,第113行,在run()文件“run.py”中,第100行,在run“filterbystore”>>beam.filter(lambda row:row['store_number'],在query_top_30_stores中)文件“l

  • 问题内容: 我有一个表,例如,具有ID,State和User_ID的Instrument作为列。 因此,我有这个JPA查询来返回具有匹配的User_ID的所有仪器记录。 它仅返回第一个记录,重复的次数与匹配记录的次数相同。 我在Db中有3条记录,仪器ID为1,2和3 我在hibernate状态下启用了show sql查询,该查询直接在数据库上运行良好,并返回了不同的记录。 hibernate查询:

  • 我在一个网站上使用angularjs,那里有一个搜索输入,可以过滤视图上的列表。此列表显示为一个ng-repeat,该ng-repeat具有搜索输入中的筛选器: 搜索输入: