ĐẶT HÀNG theo các mục phải xuất hiện trong danh sách chọn [Hoài]


7

Sử dụng Microsoft SQL Server 2008, tôi gặp lỗi sau.

Msg 104, Cấp 16, Trạng thái 1, Dòng 43
ĐẶT HÀNG theo các mục phải xuất hiện trong danh sách chọn nếu câu lệnh chứa toán tử UNION, INTERSECT hoặc EXCEPT.

Truy vấn mà tôi đang sử dụng là loại phức tạp, nhưng CASEcâu lệnh bên cạnh ORDER BYmệnh đề không thể thấy tên cột bí danh, đây là một ví dụ ngắn gọn.

SELECT 1 AS foo, 2 AS bar
UNION ALL
SELECT 10 AS foo, 20 AS bar
ORDER BY CASE WHEN foo = 2 THEN 1 END;

Trong truy vấn sản xuất của tôi, truy vấn bên trái cần được sắp xếp theo cột [360_set]được tìm thấy trong bảng và truy vấn bên phải cần được sắp xếp như thể [360_set]là null.

Làm cách nào để khắc phục lỗi này và tại sao cú pháp này tạo ra lỗi?

Đây là thông tin phiên bản,

Microsoft SQL Server Management Studio     10.0.5512.0
Microsoft Analysis Services Client Tools   10.0.5500.0
Microsoft Data Access Components (MDAC)    6.1.7601.17514
Microsoft MSXML                            3.0 6.0 
Microsoft Internet Explorer                9.10.9200.16635
Microsoft .NET Framework                   2.0.50727.5472
Operating System                           6.1.7601

Bạn không thể sắp xếp theo thứ tự cột bên trong một biểu thức ( ORDER BY 1) và truy vấn ví dụ của bạn không thể tạo ra foo = 2vì vậy tôi đã đưa ra một vài phỏng đoán về ý định này.
Martin Smith

Câu trả lời:


12

Nếu một bí danh được sử dụng trong một ORDER BYthì nó phải được sử dụng riêng, không phải trong một biểu thức.

Nếu bên trong bất kỳ loại biểu thức nào, nó cố gắng phân giải nó thành một cột trong các nguồn của bảng cơ sở chứ không phải là bí danh.

Ví dụ

SELECT A AS B
FROM   (VALUES (1, 3),
               (2, 2),
               (3, 1)) V(A, B)
ORDER  BY B

Trả về (được đặt theo bí danh)

+---+
| B |
+---+
| 1 |
| 2 |
| 3 |
+---+

Nhưng

SELECT A AS B
FROM   (VALUES (1, 3),
               (2, 2),
               (3, 1)) V(A, B)
ORDER  BY B + 0 

Trả về (Sắp xếp theo cột bảng cơ sở B)

+---+
| B |
+---+
| 3 |
| 2 |
| 1 |
+---+

Tất nhiên bạn có thể chỉ cần bọc toàn bộ trong một bảng dẫn xuất hoặc CTE.

WITH T AS
(
SELECT 1 AS foo, 2 AS bar
UNION ALL
SELECT 10 AS foo, 20 AS bar
)
SELECT *
FROM T
ORDER BY CASE WHEN foo = 1 THEN bar END;
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.