没有foreignkey的Django-queryset连接

时间:2013-10-25 12:54:35

标签: python django django-queryset

model.py

class Tdzien(models.Model):
  dziens = models.SmallIntegerField(primary_key=True, db_column='DZIENS')
  dzienrok = models.SmallIntegerField(unique=True, db_column='ROK')


class Tnogahist(models.Model):
  id_noga = models.ForeignKey(Tenerg, primary_key=True, db_column='ID_ENERG')
  dziens = models.SmallIntegerField(db_column='DZIENS')

我想要的是获取id_noga,其中dzienrok = 1234。我知道dziens应该是

dziens = models.ForeignKey(Tdzien)

但事实并非如此,我无法改变这一点。通常我会使用像

这样的东西
Tnogahist.objects.filter(dziens__dzienrok=1234)

但我不知道如何在没有外键的情况下加入和过滤这些表。

4 个答案:

答案 0 :(得分:12)

据我所知,没有外键没有连接,但你可以使用两个查询:

Tnogahist.objects.filter(dziens__in=Tdzien.objects.filter(dzienrok=1234))

答案 1 :(得分:11)

可以通过执行原始sql查询来连接两个表。但对于这种情况,这是非常讨厌的,所以我建议你重写你的models.py。

您可以查看如何执行此操作here

这将是这样的:

from django.db import connection

def my_custom_sql(self):
    cursor = connection.cursor()    
    cursor.execute("select id_noga
                    from myapp_Tnogahist a
                    inner join myapp_Tdzien b on a.dziens=b.dziens
                    where b.dzienrok = 1234")
    row = cursor.fetchone()
    return row

答案 2 :(得分:5)

您可以使用.extra执行此操作吗?来自https://docs.djangoproject.com/en/dev/ref/models/querysets/#extra

  

其中/ tables

     

您可以定义显式SQL WHERE子句 - 也许可以执行   非显式连接 - 通过使用where。您可以手动将表添加到   使用表格的SQL FROM子句。

答案 3 :(得分:2)

为了提供更多关于@paul-tomblin 的回答的背景信息,

值得一提的是对于绝大多数django用户来说;最好的做法是实现一个传统的外键。 Django 强烈建议避免使用 extra() 说“将此方法用作最后的手段”。但是,extra() 仍然优于使用 Manager.raw() 的原始查询或使用 django.db.connection

直接执行自定义 SQL

以下是如何使用 django 的 .extra() 方法实现此目标的示例:

Tnogahist.objects.extra(
    tables = ['myapp_tdzien'],
    where = [
        'myapp_tnogahist.dziens=myapp_tdzien.dziens',
        'myapp_tdzien.dzienrok=%s',
        ],
    params = [1234],
    )

与其他方法相比,使用 extra() 的主要吸引力在于它可以很好地与 django 的查询集堆栈的其余部分配合使用,例如过滤器、排除、延迟、值和切片。所以你可以将它与传统的 django 查询逻辑一起插入。例如:Tnogahist.objects.filter(...).extra(...).values('id_noga')[:10]