những gì tôi đang cố gắng làm là:
nhận 30 tác giả có điểm cao nhất (
Author.objects.order_by('-score')[:30]
)đặt hàng các tác giả bởi
last_name
Bất kỳ đề xuất?
những gì tôi đang cố gắng làm là:
nhận 30 tác giả có điểm cao nhất ( Author.objects.order_by('-score')[:30]
)
đặt hàng các tác giả bởi last_name
Bất kỳ đề xuất?
Câu trả lời:
Thế còn
import operator
auths = Author.objects.order_by('-score')[:30]
ordered = sorted(auths, key=operator.attrgetter('last_name'))
Trong Django 1.4 và mới hơn, bạn có thể đặt hàng bằng cách cung cấp nhiều trường.
Tham khảo: https://docs.djangoproject.com/en/dev/ref/models/querysets/#order-by
order_by (* trường)
Theo mặc định, các kết quả trả về bởi a QuerySet
được sắp xếp theo bộ thứ tự được cung cấp bởi ordering
tùy chọn trong Meta của mô hình. Bạn có thể ghi đè điều này trên cơ sở per-QuerySet bằng cách sử dụng order_by
phương pháp này.
Thí dụ:
ordered_authors = Author.objects.order_by('-score', 'last_name')[:30]
Kết quả trên sẽ được sắp xếp theo score
thứ tự giảm dần, sau đó last_name
tăng dần. Dấu âm phía trước "-score"
cho biết thứ tự giảm dần. Thứ tự tăng dần được ngụ ý.
lambda x: x.last_name
? Nó ngắn hơn, dài hơn và không cần nhập bất kỳ.
Tôi chỉ muốn minh họa rằng các giải pháp tích hợp sẵn (chỉ dành cho SQL) không phải lúc nào cũng là những giải pháp tốt nhất. Lúc đầu, tôi nghĩ rằng vì QuerySet.objects.order_by
phương thức của Django chấp nhận nhiều đối số, bạn có thể dễ dàng xâu chuỗi chúng:
ordered_authors = Author.objects.order_by('-score', 'last_name')[:30]
Nhưng, nó không hoạt động như bạn mong đợi. Trường hợp cụ thể, đầu tiên là danh sách các tổng thống được sắp xếp theo điểm số (chọn top 5 để dễ đọc hơn):
>>> auths = Author.objects.order_by('-score')[:5]
>>> for x in auths: print x
...
James Monroe (487)
Ulysses Simpson (474)
Harry Truman (471)
Benjamin Harrison (467)
Gerald Rudolph (464)
Sử dụng giải pháp của Alex Martelli cung cấp chính xác 5 người hàng đầu được sắp xếp theo last_name
:
>>> for x in sorted(auths, key=operator.attrgetter('last_name')): print x
...
Benjamin Harrison (467)
James Monroe (487)
Gerald Rudolph (464)
Ulysses Simpson (474)
Harry Truman (471)
Và bây giờ là order_by
cuộc gọi kết hợp :
>>> myauths = Author.objects.order_by('-score', 'last_name')[:5]
>>> for x in myauths: print x
...
James Monroe (487)
Ulysses Simpson (474)
Harry Truman (471)
Benjamin Harrison (467)
Gerald Rudolph (464)
Như bạn có thể thấy, kết quả giống như kết quả đầu tiên, có nghĩa là nó không hoạt động như bạn mong đợi.
Đây là một cách cho phép quan hệ đối với điểm giới hạn.
author_count = Author.objects.count()
cut_off_score = Author.objects.order_by('-score').values_list('score')[min(30, author_count)]
top_authors = Author.objects.filter(score__gte=cut_off_score).order_by('last_name')
Bạn có thể có hơn 30 tác giả trong top_authors theo cách này và điều min(30,author_count)
đó xảy ra nếu bạn có ít hơn 30 tác giả.