TIL96. select_related , prefetch_related

5395 ワード

select relatedとprefetch relatedとは何ですか?


select relatedおよびprefetch relatedは、1つのQuerySetをインポートするときに、関連するすべてのオブジェクトを事前にロードする関数です.
queryは複雑になりますが、ロードされたデータがcacheに残っているため、データベースへの再アクセスが必要な問題が減少する可能性があります.
どちらもDBへのアクセス数を減らしています.
ダイエット!

select relatedとprefetch relatedの違い


select_related

  • 正参照(M:1)または1:1関係で使用できます.
  • データは、JOINの1回のクエリにより、多かれ少なかれすべての情報を取得する.
  • 1回の呼び出し
  • クエリは有効ですが、データが多い場合、応答速度が遅くなる可能性があります.
  • prefetch_related

  • 多対多(M:M)、逆参照の場合に使用できますが、一対一、Foreign keyなどのすべての関係でも使用できます.
  • JOINの個別クエリーを実行しない場合、Djangoは直接データを結合します.(2回以上のクエリ)
  • Dog.objects.all()		     # Dog테이블 1번, Dog를 소유하고 있는 User마다 DB 방문 // 쿼리 폭탄😭
    Dog.objects.select_related('User')   # inner join쿼리 수행 // 쿼리 1번 수행
    Dog.objects.prefetch_related('User') # Dog조회, User조회 // 쿼리 2번 수행
    prefetch related()、select related()カッコに入る()만 사용할거야!と解釈すれば簡単です.
    使用するテーブルのみインポートまたは追加!!
    >>> Notification.objects.prefetch_related('company').filter(id=2)
    <QuerySet [<Notification: Notification object (2)>]>     -- 정참조
    
    
    >>> Notification.objects.prefetch_related('image_set').filter(id=2)
    <QuerySet [<Notification: Notification object (2)>]>     -- 역참조 _set붙히기
    
    
    >>> Notification.objects.prefetch_related('tag').filter(tag__id=2)
    <QuerySet [<Notification: Notification object (2)>, <Notification: Notification object (7)>, <Notification: Notification object (12)>, <Notification: Notification object (17)>, <Notification: Notification object (22)>, <Notification: Notification object (27)>, <Notification: Notification object (32)>
    --MTM 관계

    エクスペリエンスクエリコール回数



    MyUser.objects.all()を使用して合計何回クエリーを呼び出しますか?
    答えは全部で4番です
    MyUserモデルデータを取得するためのクエリー
    MyUserモデルに入力された3つのデータのうち、OneToOne接続の会社モデルを入力するためのクエリーは3つあります.

    今回はMyUserobjects.select_related('company').私はall()で会社のすべての型番を持ってきます!

    今度の問い合わせの呼び出し回数は1番です!
    MyUserに100社と100人のOneToOneユーザーがいたら、
    MyUser.objects.all()を使用すると、MyUserは101回のクエリーを実行します.objects.select_related('company').all()は、1つのクエリーでのみすべてのデータを取得できます.
    同じ条件のDBでMyUser.objects.prefetch_related('company').クエリーセットをall()にインポートします.

    今回は2つのクエリーを実行しました.