Мога ли да използвам декларацията CASE в условие JOIN?

Следващото изображение е част от Microsoft SQL Server 2008 R2 System Views. От изображението се вижда, че връзката между sys.partitions и sys.allocation_units зависи от стойността на sys.allocation_units.type. Така че, за да ги обединя, ще напиша нещо подобно на това:

SELECT  *
FROM    sys.indexes i
        JOIN sys.partitions p
            ON i.index_id = p.index_id 
        JOIN sys.allocation_units a
            ON CASE
               WHEN a.type IN (1, 3)
                   THEN a.container_id = p.hobt_id 
               WHEN a.type IN (2)
                   THEN a.container_id = p.partition_id
               END 

Но горният код дава синтактична грешка. Предполагам, че това се дължи на оператора CASE. Може ли някой да помогне да обясни малко?


Добавете съобщение за грешка:

Msg 102, Level 15, State 1, Line 6 Неправилен синтаксис близо до '='.

Решение

Изразът CASE връща стойност от частта THEN на клаузата. Можете да го използвате по следния начин:

SELECT  * 
FROM    sys.indexes i 
    JOIN sys.partitions p 
        ON i.index_id = p.index_id  
    JOIN sys.allocation_units a 
        ON CASE 
           WHEN a.type IN (1, 3) AND a.container_id = p.hobt_id THEN 1
           WHEN a.type IN (2) AND a.container_id = p.partition_id THEN 1
           ELSE 0
           END = 1

Обърнете внимание, че трябва да направите нещо с върнатата стойност, например да я сравните с 1. Вашето изречение се опитва да върне стойността на присвояване или да провери равенство, като нито едно от двете няма смисъл в контекста на клауза CASE/THEN``. (АкоBOOLEAN` беше тип данни, тогава тестът за равенство би имал смисъл.)

Коментари (6)

Вместо това просто се присъединявате към двете таблици и в клаузата SELECT, връщате данни от тази, която съвпада:

Предлагам ви да прегледате тази връзка Conditional Joins in SQL Server и https://stackoverflow.com/questions/8361183/t-sql-case-statement-in-a-join-on-clause

напр.

    SELECT  *
FROM    sys.indexes i
        JOIN sys.partitions p
            ON i.index_id = p.index_id 
        JOIN sys.allocation_units a
            ON a.container_id =
            CASE
               WHEN a.type IN (1, 3)
                   THEN  p.hobt_id 
               WHEN a.type IN (2)
                   THEN p.partition_id
               END 

Редактиране: Съгласно коментарите.

Не можете да посочите условието за присъединяване, както правите.. Проверете заявка по-горе, че няма грешка. Извадил съм общата колона нагоре и стойността на дясната колона ще бъде оценена по условието.

Коментари (9)

Опитайте това:

...JOIN sys.allocation_units a ON 
  (a.type=2 AND a.container_id = p.partition_id)
  OR (a.type IN (1, 3) AND a.container_id = p.hobt_id)
Коментари (1)