Столбец sys.objects.type_desc не будет совпадать с якорем в рекурсивном CTE

У меня есть следующий CTE:

;WITH Cte([Type], [Level]) AS 
(
SELECT CONVERT(NVARCHAR(60), 'USER_TABLE'), 1

UNION ALL

SELECT CONVERT(NVARCHAR(60), o.type_desc), Cte.[Level] + 1
FROM sys.objects o
JOIN Cte ON 1 = 1
WHERE Level < 3
)
SELECT * FROM Cte

И он возвращает мне сообщение "Типы не совпадают между якорем и рекурсивной частью в столбце" Тип "рекурсивного запроса" Cte ".' Предполагается, что sys.objects.type_desc должен быть NVARCHAR(60), поэтому не нужно использовать CONVERT для него, но после получения ошибки, чтобы я не добавил ее, чтобы быть уверенным или что-то в этом роде.

Если я удаляю JOIN на Cte в рекурсивной части и жестко кодирую [Level], чтобы CTE больше не был рекурсивным, SQL работает нормально. Если я вставлю содержимое sys.objects в временную таблицу и заменим sys.objects в рекурсивной части CTE временной таблицей, SQL будет работать нормально. Любая попытка использовать CAST вместо CONVERT или изменить тип назначения с NVARCHAR(60) на другой NVARCHAR или VARCHAR не приводит к изменению результата.

Есть идеи, что здесь происходит?

Спасибо

(Также очевидно, что SQL бесполезен, это всего лишь пример, который воспроизводит ошибку, с которой я столкнулся при работе с большим кодом.)

РЕДАКТИРОВАТЬ: Следует также добавить, я запускаю SQL Server 2012 здесь (хотя я тоже пробовал то же самое в 2014 году и у меня была та же проблема).

1 ответ

Обновление: было основано на предыдущей версии вопроса, которая соединялась с таблицей #tmp, а не с sys.objects

Это похоже на разницу в сопоставлении между tempdb и текущей базой данных. Обычно это происходит, если вы устанавливаете сервер SQL с одним сопоставлением и создаете / восстанавливаете БД с другим сопоставлением.

Системные базы данных будут использовать параметры сортировки. Чаще всего вызывает проблемы с таблицами #tmp.

(Ответ основан на том факте, что предложение Мартина Смита устранило проблему)

Другие вопросы по тегам