1

我正在尝试根据 ID 和位置获取下一个最新条目的信息,并将其添加到我正在运行的查询中。不是表中第二个最近的条目,只有基于 ID 的上一个条目。

我不确定这是否可能,或者我只是不知道该怎么做,甚至不知道我应该往哪个方向走。

这是以前的程序员是如何做到的:

SELECT -- blah blah blah
       , (SELECT TOP 1 CAST(id AS VARCHAR) + '~' + CONVERT(VARCHAR,  creation_date,   120)
          FROM header hdr2 
          WHERE hdr2.id < hdr.id 
                AND hdr2.location = hdr.location 
          ORDER BY hdr2.id DESC) AS "prev_info"
FROM header hdr 
/*blah blah blah*/

我理解他为什么只想使用单个子查询并试图将所有内容放入该列中,但我正在尝试优化这一点,我想以其他更简单、更有效的方式来做。

我觉得答案正盯着我的脸,但我无法伸手去抓住它。如果我需要进一步解释自己,请不要犹豫。

4

3 回答 3

2

如果您想使用 ROW_NUMBER,我认为这会起作用:

With rownumbers as 
(
  SELECT
    ROW_NUMBER() OVER (partition by location ORDER BY id ASC) AS rownumber,
    id, location
  FROM header 
)
SELECT id, location from rownumbers
WHERE rownumber = 2

这更容易阅读吗?我会说这取决于读者。这样更有效率吗?我得看看执行计划。

于 2012-06-05T17:44:54.473 回答
1

考虑使用outer apply

select  -- blah blah blah
,       prev_info.*
from    header hdr 
outer apply
        (
        select  top 1 id
        ,       creation_date
        from    header hdr2 
        where   hdr2.id < hdr.id 
                and hdr2.location = hdr.location 
        order by
                hdr2.id desc
        ) as prev_info
于 2012-06-05T17:39:09.787 回答
1

如果我理解正确,您可以使用交叉应用一次获取所有列。

SELECT -- blah blah blah
FROM header hdr 
  cross apply(
          SELECT TOP 1
            hdr2.*
          FROM header hdr2 
          WHERE hdr2.id < hdr.id 
                AND hdr2.location = hdr.location 
          ORDER BY hdr2.id DESC
) AS prev_info
/*blah blah blah*/

与您拥有的选择中的子查询做同样的事情,除了允许返回多于一列,因此您不必从一个连接列中解析出所有内容。

于 2012-06-05T17:39:16.537 回答