Sqlserver
 sql >> база данни >  >> RDS >> Sqlserver

LAST_VALUE в SQL Server 2012 връща странни резултати

SQL Server не знае и не се интересува от реда, в който редовете са били вмъкнати в таблицата. Ако имате нужда от конкретна поръчка, винаги използвайте ORDER BY . Във вашия пример ORDER BY е двусмислено, освен ако не включите PK в ПОРЪЧАЙ ПО . Освен това LAST_VALUE функцията може да върне странни резултати, ако не сте внимателни - вижте по-долу.

Можете да получите очаквания резултат, като използвате MAX или LAST_VALUE (SQLFiddle ). Те са еквивалентни в този случай:

SELECT
    PK, Id1, Id2
    ,MAX(PK) OVER (PARTITION BY Id1, Id2) AS MaxValue
    ,LAST_VALUE(PK) OVER (PARTITION BY Id1, Id2 ORDER BY PK rows between unbounded preceding and unbounded following) AS LastValue
FROM
    Data
ORDER BY id1, id2, PK

Резултатът от тази заявка ще бъде същият, независимо от реда, в който първоначално са били вмъкнати редовете в таблицата. Можете да опитате да поставите INSERT изявления в различен ред във цигулката. Това не влияе на резултата.

Освен това LAST_VALUE не се държи точно както бихте очаквали интуитивно с прозореца по подразбиране (когато имате само ORDER BY в НАД клауза). Прозорецът по подразбиране е РЕДОВЕ МЕЖДУ НЕОГРАНИЧЕН ПРЕДИШЕН И ТЕКУЩ РЕД , докато очаквахте да бъде РЕДОВЕ МЕЖДУ НЕОГРАНИЧЕНО ПРЕДИШНО И НЕОГРАНИЧЕНО СЛЕДВАЩО . Ето SO отговор с добро обяснение . Връзката към този SO отговор е на страницата на MSDN за LAST_VALUE . Така че, след като прозорецът на реда е посочен изрично в заявката, той връща това, което е необходимо.

Ако искате да знаете реда, в който редовете са били вмъкнати в таблицата, мисля, че най-простият начин е да използвате САМОЛИЧНОСТ . И така, дефиницията на вашата таблица ще се промени на това:

CREATE TABLE Data 
(PK INT IDENTITY(1,1) PRIMARY KEY,
Id1 INT,
Id2 INT)

Когато INSERT в тази таблица не е необходимо да указвате стойността за PK , сървърът ще го генерира автоматично. Той гарантира, че генерираните стойности са уникални и нарастващи (с положителен параметър за нарастване), дори ако имате много клиенти, които вмъкват в таблицата едновременно. Възможно е да има пропуски между генерираните стойности, но относителният ред на генерираните стойности ще ви каже кой ред е вмъкнат след кой ред.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Как да увеличите допустимия размер на прикачените файлове при изпращане на имейл в SQL Server (T-SQL)

  2. Грешка при избор на данни от таблица в SQL Server

  3. Случай в изявление за избор

  4. Бърз скрипт, който връща всички свойства от SERVERPROPERTY() в SQL Server 2017/2019

  5. Добра практика ли е REPLACE INTO?