Đặt hàng theo giá trị trường cụ thể trước tiên


91

Tôi có một bảng với 3 cột:

id | name | priority
--------------------
 1 | core  |   10
 2 | core  |   9
 3 | other |   8
 4 | board |   7
 5 | board |   6
 6 | core  |   4

Tôi muốn sắp xếp tập hợp kết quả bằng cách sử dụng prioritynhưng trước tiên những hàng name=corecó mức độ ưu tiên thấp hơn. Kết quả sẽ như thế này

id | name | priority
--------------------
 6 | core  |   4
 2 | core  |   9
 1 | core  |   10
 5 | board |   6
 4 | board |   7
 3 | other |   8

Câu trả lời:


159

Ngoài ra còn có chức năng MySQLFIELD .

Nếu bạn muốn sắp xếp hoàn chỉnh cho tất cả các giá trị có thể:

SELECT id, name, priority
FROM mytable
ORDER BY FIELD(name, "core", "board", "other")

Nếu bạn chỉ quan tâm rằng "cốt lõi" là trên hết và các giá trị khác không quan trọng:

SELECT id, name, priority
FROM mytable
ORDER BY FIELD(name, "core") DESC

Nếu bạn muốn sắp xếp theo "lõi" trước và các trường khác theo thứ tự sắp xếp thông thường:

SELECT id, name, priority
FROM mytable
ORDER BY FIELD(name, "core") DESC, priority

Tuy nhiên, có một số lưu ý ở đây:

Đầu tiên, tôi khá chắc rằng đây là chức năng chỉ dành cho mysql - câu hỏi được gắn thẻ mysql, nhưng bạn không bao giờ biết.

Thứ hai, hãy chú ý đến cách FIELD()hoạt động: nó trả về chỉ mục dựa trên một giá trị - trong trường hợp FIELD(priority, "core"), nó sẽ trả về 1 nếu "core" là giá trị. Nếu giá trị của trường không có trong danh sách, nó sẽ trả về giá trị không . Đây là lý do tại sao DESCcần thiết trừ khi bạn chỉ định tất cả các giá trị có thể.


5
Sau khoảng 5 năm, tôi đã thay đổi câu trả lời được chấp nhận cho câu trả lời này vì nó sạch hơn và nhanh hơn.
Omid

db2 tương đương?
Cybermonk

Nó hoạt động với tôi, tôi muốn hỏi thêm một câu hỏi về cách xử lý Nếu cột 'ưu tiên' chứa các giá trị như: 'lõi đất', 'bảng mới', v.v. Ở đây cột không chứa giá trị chính xác, chúng ta có thể viết một cái gì đó như %cốt lõi%?
Jayanth Suvarna

@JayanthSuvarna: xem xét tài liệu MySQL FIELD (), tôi khá chắc chắn rằng không có cách nào để đánh giá đây là chuỗi con, vì mỗi đối số phải là một loại chuỗi. Có thể có một số hàm thao tác chuỗi có thể hữu ích, nhưng tôi không chắc.
Nerdmaster

Cảm ơn, anh bạn. Bạn đã làm nên ngày của tôi.
BEingprabhU

92

Nói chung bạn có thể làm

select * from your_table
order by case when name = 'core' then 1 else 2 end,
         priority 

Đặc biệt trong MySQL, bạn cũng có thể làm

select * from your_table
order by name <> 'core',
         priority 

Vì kết quả của một phép so sánh trong MySQL là 0hoặc 1và bạn có thể sắp xếp theo kết quả đó.


1
những gì hiện 12phương tiện ở đây?
Niraj Chauhan

1
Tôi có khoảng 3000 hàng để sắp xếp. Trong trường hợp của tôi, giải pháp của @ Ayman-Hourieh trên stackoverflow.com/questions/958627/… mất một nửa thời gian so với giải pháp này.
đêm vào

@nightlyop: Tốt. Chỉ một lưu ý: Giải pháp nhanh hơn là dành riêng cho MySQL.
juergen d

12chỉ là 2 số tôi sử dụng để sắp xếp dữ liệu. Có thể là 34hoặc cái gì khác.
juergen d

Còn khi có %trong WHEREmệnh đề thì sao? Như . . . WHERE name LIKE '%sth%' . . .thế nào? stackoverflow.com/questions/41303379/…
ngăn xếp

6

Một cách để ưu tiên cho các hàng cụ thể là thêm một số lớn vào mức ưu tiên của chúng. Bạn có thể làm điều này với một CASEcâu lệnh:

  select id, name, priority
    from mytable
order by priority + CASE WHEN name='core' THEN 1000 ELSE 0 END desc

Demo: http://www.sqlfiddle.com/#!2/753ee/1


5

Điều này phù hợp với tôi khi sử dụng Postgres 9+:

SELECT *
FROM your_table
ORDER BY name = 'core' DESC, priority DESC

Bạn muốn giải thích -1? Lỗi + Phiên bản Postgres?
Vojtech Vitek

3

Một cách là:

select id, name, priority from table a
order by case when name='core' then -1 else priority end asc, priority asc

1
Điều này sẽ không làm mất thứ tự của các corehàng?
mellamokb,

1
SELECT * FROM cars_new WHERE status = '1' and car_hide !='1' and cname IN ('Executive Car','Saloon','MPV+','MPV5') ORDER BY FIELD(cname, 'Executive Car', 'Saloon','MPV+','mpv5')

3
Mặc dù mã của bạn có thể là câu trả lời cho câu hỏi, nhưng tốt hơn là bạn nên cung cấp một số giải thích về nó.
Mehraban

0

làm cái này:

SELECT * FROM table ORDER BY column `name`+0 ASC

Thêm +0 sẽ có nghĩa là:

0, 10, 11, 2, 3, 4

trở thành:

0, 2, 3, 4, 10, 11

Kỹ thuật này là để biến một chuỗi thành một số. Nó không giải quyết câu hỏi của OP. (Tuy nhiên, không nhìn thấy loại dữ liệu của priority, tôi không thể nói liệu nó có phải là một phần của giải pháp hoàn chỉnh hay không.)
Rick James

0

Dùng cái này:

SELECT * 
FROM tablename 
ORDER BY priority desc, FIELD(name, "core")
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.