2009-01-24 47 views
26

Hãy nói rằng tôi có mô hình sau:thứ tự một QuerySet bằng giá trị trường tổng hợp

class Contest: 
    title = models.CharField(max_length = 200) 
    description = models.TextField() 

class Image: 
    title = models.CharField(max_length = 200) 
    description = models.TextField() 
    contest = models.ForeignKey(Contest) 
    user = models.ForeignKey(User) 

    def score(self): 
     return self.vote_set.all().aggregate(models.Sum('value'))[ 'value__sum' ] 

class Vote: 
    value = models.SmallIntegerField() 
    user = models.ForeignKey(User) 
    image = models.ForeignKey(Image) 

Người sử dụng của một trang web có thể góp phần hình ảnh của họ cho một số cuộc thi. Sau đó, những người dùng khác có thể bỏ phiếu cho họ lên hoặc xuống. Mọi thứ hoạt động tốt, nhưng bây giờ tôi muốn hiển thị một trang mà người dùng có thể xem tất cả các đóng góp cho một cuộc thi nhất định. Các hình ảnh sẽ được sắp xếp theo điểm số của chúng. Vì vậy, tôi thử như sau:

Contest.objects.get(pk = id).image_set.order_by('score') 

Như tôi sợ nó không hoạt động kể từ 'điểm' không có lĩnh vực cơ sở dữ liệu có thể được sử dụng trong các truy vấn.

Trả lời

47

Ồ, tất nhiên tôi quên hỗ trợ tập hợp mới ở Django và chức năng annotate của nó.

Vì vậy, truy vấn có thể trông như thế này:

Contest.objects.get(pk=id).image_set.annotate(score=Sum('vote__value')).order_by('score') 
+0

Giải pháp tuyệt vời! :) – okoman

+0

Tôi nhận được kết quả ra khỏi trật tự ... chúng hầu hết là theo thứ tự, nhưng một số trong số chúng bị thất lạc ... điều gì có thể gây ra điều đó? – Jiaaro

+0

Đây là giải pháp chỉ dành cho trường hợp cụ thể đó chứ không phải cho tiêu đề câu hỏi: "QuerySet order by method". Đây không phải là giải pháp để đặt hàng một queryset theo phương thức: @ S.Lott response là giải pháp đúng cho trường hợp chung –

9

Bạn có thể viết sắp xếp của riêng bạn bằng Python rất đơn giản.

def getScore(anObject): 
    return anObject.score() 
objects= list(Contest.objects.get(pk = id).image_set) 
objects.sort(key=getScore) 

Điều này rất hữu ích vì chúng tôi đã sắp xếp danh sách mà chúng tôi sẽ cung cấp cho mẫu.

+0

Vâng, bạn có thể. Bạn chỉ cần thực hiện tổng số như một phần của truy vấn. –

+0

Đối tượng 'Người quản lý liên quan' không có thuộc tính 'sắp xếp' : ( – okoman

+2

@okoman ... có nghĩa là bạn không chuyển đổi sang danh sách bằng cách sử dụng hàm list() – Jiaaro

1

Cấp db order_by không thể sắp xếp truy vấn theo phương pháp python của mô hình.

Giải pháp là giới thiệu trường score thành mô hình Image và tính toán lại nó trên mọi cập nhật Vote. Một số loại không chuẩn hóa. Khi bạn có thể sắp xếp theo nó.

+0

Tôi không chắc chắn đó là giải pháp * tốt nhất *, nhưng nó là giải pháp * a * –

+0

Ồ, vâng, tôi đồng ý. –

Các vấn đề liên quan