2011-09-12 130 views
1

我是新來的Django,我覺得這是一個簡單的問題 -Django的過濾器返回多個值

我有編碼如下一個中間類 -

class Link_Book_Course(models.Model): 
    book = models.ForeignKey(Book) 
    course = models.ForeignKey(Course) 
    image = models.CharField(max_length = 200, null=True) 
    rating = models.CharField(max_length = 200,null=True) 
    def __unicode__(self): 
     return self.title 
    def save(self): 
     self.date_created = datetime.now() 
     super(Link_Book_Course,self).save() 

我在做這個打電話,因爲我想必須有所有的書籍的作者(書是一種模型,筆者作爲一名CharField)

storeOfAuthorNames = Link_Book_Course.objects.filter(book__author) 

但是,它不會返回所有作者的一個QuerySet,實際上,它會拋出一個錯誤。

我認爲這是因爲book__author有多個值 - 我怎麼能得到所有這些值?

謝謝!

+0

要查詢給定書籍的所有作者或者Link_Book_Course中提及的至少一本書的所有作者嗎? – ftartaggia

回答

0

你試圖使用過濾器的方法轉化或多或少成這樣的SQL:

SELECT * FROM Link_Book_Course INNER JOIN書(...),其中Book.author =;

所以當你看到你的查詢有一個不完整的where子句。

無論如何,這不是你正在尋找的查詢。

的東西像什麼(假設作者是本書的一個簡單的文本字段,你想從Link_Book_Course情況僅指書的作者):

Book.objects.filter(pk__in = Link_Book_Course.objects.all() .values_list(「book」,flat = True))。values_list(「author」,flat = True)

+0

我不會推薦一個使用這樣的查詢,它非常不高效。 –

+0

正確。任何建議? – ftartaggia

+0

哦,是的,nrabinowitz的回答得到了重點! – ftartaggia

0

首先,過濾器語句過濾匹配某個模式的字段。所以如果Book有一個簡單的ForeignKey作者,你可以有
storeOfAuthorNames = Link_Book_Course.objects.filter(book__author="Stephen King"),但不只是
storeOfAuthorNames = Link_Book_Course.objects.filter(book__author)

一旦你過去,我猜書有作者爲ManyToManyField,不是ForeignKey(因爲一本書可以有多個作者,一個作者可以發佈多書嗎?)在這種情況下,只是filter(book__author="Stephen King")意願依然不足夠。嘗試Link_Book_Course.objects.filter(book_author__in=myBookObject.author.all())

3

我不認爲你正在使用正確的queryset方法。 filter()過濾器通過它的參數 - 這樣的預期的用法是:

poe = Author.objects.get(name='Edgar Allen Poe') 
course_books_by_poe = Link_Book_Course.objects.filter(book__author=poe) 

它看起來像你想拉的名單在特定過程中使用的所有書籍的作者(或者所有課程?) 。也許你正在尋找.values()values_list()

all_authors_in_courses = Link_Book_Course.objects.values_list(
     'book__author', flat=True 
    ).distinct() 

編輯:每@ ftartaggia的建議更新)

+0

如何在最後一條語句中添加一個distinct(),如果方便的話,使用values_list('book_author',flat = True)如何? – ftartaggia

+0

@ftartaggia - 兩個很好的建議,現在包括在內。 – nrabinowitz

1

正如其他人已經解釋的,使用過濾器的方法是讓全組對象的一個​​子集,不返回其他實例模型(無論相關的對象或左右)

如果你想有作者模型的實例從Django的ORM回來,你可以使用聚合的API,那麼你可能需要做這樣的事情:

from django.db.models import Count 
Author.objects.annotate(num_books=Count('book')).filter(num_books__gt=1)