Многокомпонентный идентификатор не может быть связан, коррелированный подзапрос - PullRequest
0 голосов
/ 28 июня 2010

Это надуманный пример использования SQL Server 2008.

По сути, я храню список идентификаторов в столбце xml в таблице: temp (bigint id, xml ids)

Я хочу присоединить саму таблицу к узлам xml.

Пока у меня есть:

select * from temp x
join (
    select  x.id
    ,   ids.id.value('@value', 'bigint') zid 
    from    temp t cross apply ids.nodes('/ids/id') as ids(id)
) z on x.id=z.id

Я получаю: Не удалось связать идентификатор из нескольких частей "x.id".

Для меня это выглядит как обычный коррелированный подзапрос.Чего мне не хватает?

----- обновление:

Для следующих примеров данных во временной таблице:

id ids
-- ---
 1 <ids><id value="11" /><id value="12" /><id value="13" /></ids>
 2 <ids><id value="21" /><id value="22" /><id value="23" /></ids>
 3 <ids><id value="31" /><id value="32" /><id value="33" /></ids>

Я ожидал увидеть следующеекак результат набора:

id zid
-- ---
 1  11
 1  12
 1  13
 2  21
 2  22
 2  23
 3  31
 3  32
 3  33

Ответы [ 2 ]

1 голос
/ 28 июня 2010

Это производная таблица, а не коррелированный подзапрос. Обратите внимание, что это тоже не работает.

WITH TEMP AS
(
SELECT 1 AS id
)

select x.id 
from temp x
join (
select  x.id,*  from temp t
) z
on  x.id  =  z.id 

Из MSDN производная_таблица

Подзапрос, который извлекает строки из база данных. производная_таблица используется как ввод во внешний запрос.

, так что это сильно отличается от коррелированного подзапроса , где

подзапрос зависит от внешнего запросить его значения. Это означает, что подзапрос выполняется повторно, один раз для каждой строки, которая может быть выбирается внешним запросом.

Чтобы получить ожидаемый результат, вам вовсе не нужен JOIN.

WITH TEMP AS
(
select 1 as id, CAST('<ids><id value="11" /><id value="12" /><id value="13" /></ids>' as xml) as ids UNION ALL
select 2, '<ids><id value="21" /><id value="22" /><id value="23" /></ids>' UNION ALL
select 3, '<ids><id value="31" /><id value="32" /><id value="33" /></ids>'

)

 select 
 t.id,
 ids.id.value('@value', 'bigint') zid 
 from    temp t cross apply ids.nodes('/ids/id') as ids(id)

Если вы решили использовать один из них, ответ despart был верным.

select x.id, zid  from temp x
join (
    select 
    t.id,
    ids.id.value('@value', 'bigint') zid 
    from    temp t cross apply ids.nodes('/ids/id') as ids(id)
) z on x.id=z.id
0 голосов
/ 28 июня 2010

Вы выбираете x.id внутри подзапроса, возможно, вам следует выбрать t.id?

...