2011-11-11 104 views
7

關係我有4款車型,我想找回它們MODELADjango的逆轉與select_related

class ModelA(models.Model): 
    product = models.ForeignKey(ModelB) 
    group = models.ForeignKey(Group) 

之間

聯接ModelB

class ModelB(models.Model): 
    title = models.CharField() 

ModelC

class ModelC(models.Model): 
    product = models.ForeignKey(ModelB) 
    group = models.ForeignKey(ModelD) 

ModelD

class ModelD(models.Model): 
    name = models.CharField() 

現在我想我所有的MODELA對象與加入ModelBModelCModelD 在SQL這是很容易的事。只需在表格之間進行連接。 與Django的ORM我卡住,因爲我只能做前進的關係。

我這樣做

ModelA.objects.all().select_related(product) 

但我不能參加ModelC 我已經讀this article,但我不想遍歷我的大名單,做一個簡單的事情!我只想打一次數據庫。

我使用的Django的最後一個版本,我希望已經有到了一個解決方案,我是不知道的。

謝謝。

+0

你有沒有嘗試過這樣的事情: 'ModelA.objects.all()。select_related('product','product__modelc','product__modelc__group')' ?不發佈這個作爲答案,因爲我不是絕對相信,如果它是你想要的。 –

+1

@bildja:'select_related'不支持遍歷。 –

回答

8

參見prefetch_related文檔。目前它只是開發,但會用Django 1.4。如果你可以等,或者你可以在後備箱上跑。你將可以使用它。

在此期間,您可以嘗試django-batch-select。它基本上服務於相同的目的。

3

編輯:重讀問題後,解決的辦法是不那麼簡單。

docs說:

select_related僅限於單值關係 - 外鍵 和一個對一個。

Django 1.4 querysets將有prefetch_related方法,您應該一定閱讀。這聽起來像你不能在一個單一的查詢中完成,但你可能能夠在2或3中完成它。你應該一定要看看,如果你真的需要升級到dev版本。

如果你不能使用的是開發版本,並不能等待1.4,則Django還支持custom SQL queries

+0

正確。 'prefetch_related'不會在像select_related這樣的單個查詢中完成。簡而言之,沒有辦法做到這一點。這意味着如此循環通過相關項目的n + 1查詢問題會導致每個循環的查詢。相反,它首先爲關係執行單個查詢,然後緩存結果以供稍後使用。 –