Queryset получает только одну (любую) запись для каждого внешнего ключа

Скажем, у меня есть следующие модели:

class Manufacturer(Model):
    name = models.CharField(max_length=255)
    origin = models.CharField(max_length=255)

class Car(Model):
    model = models.CharField(max_length=255)
    manf = models.ForeignKey(Manufacturer, related_name="cars")

И тогда я хочу выполнить следующий запрос:

usa_manfs = Manufacturer.objects.filter(origin='USA')
usa_manf_cars = Car.objects.filter(manf__in=usa_manfs)

Однако я бы хотел, чтобы в QuerySet был только 1 автомобиль на одного производителя.

Я знаю, что могу пойти другим путем и сделать что-то вроде usa_manfs.cars[0] однако не означает ли это, что мне нужно сделать запрос для каждого производителя, чтобы получить все связанные автомобили?

Чтобы уточнить, мне не нужно никакого контроля над тем, какой экземпляр Car извлекается по отношению к каждому производителю. Мне просто нужно составить список автомобилей, в которых производитель уникален.

РЕШЕНИЕ ДЛЯ ТЕПЕРЬ

После долгих размышлений я решил пойти на решение Python и предотвратить дублирование в цикле.

У данных, с которыми я работаю, скорее всего, будет относительно небольшое количество дубликатов (в которых мой пример, возможно, не будет работать) в поле ForeignKey, и, поскольку я не могу заставить работать решение, которое хранит его в Django ORM, я Я просто отслеживаю ForeignKey и исключаю повторения в цикле. Так как я все равно зацикливаюсь на них, я не думаю, что в целом создаю гораздо больше работы.

например:

cars = list(Car.objects.all())
final_list = []
used_before = []

for car in cars:
    if not car.manf_id in used_before:
        used_before.append(car.manf_id)
        doStuff(car)
        final_list.append(car)

Если найдется лучшее решение, я его приму.

2 ответа

Мне просто нужно закончить со списком Cars где Manufacturer уникален

Как насчет использования distinct:

cars = Car.objects.order_by('manf').distinct('manf')

Поскольку вышеперечисленное поддерживается только в PostgreSQL, вы должны обойти это:

m = Manufacturer.objects.all()

cars = []
for i in m:
    if Car.objects.filter(manf=i).exists():
       cars.append(Car.objects.filter(manf=i).order_by('?')[1])

Это даст вам одну случайную машину для каждого производителя.

Я не уверен, как мы можем сделать это с помощью Orm. Можете рассказать, как мы можем добиться этого через прямой sql:

from django.db import connection
cursor = connection.cursor()

cursor.execute("select c.model from myapp_car c, myapp_manufacturer m where m.origin='USA' and m.id=c.manf_id group by m.id")
Другие вопросы по тегам