дополнительный код из модели поможет, потому что это трудно понять, что QuerySet «Позиции» содержит.
Я постараюсь помочь в любом случае ...
Потому что вы смоделировали отношения между пользователями и элементами, нет необходимости перебирать каждый пункт в этом QuerySet, когда вы можете просто выбрать подмножество, которые являются Вам интересно.
Опять же, у меня немного трудностей следующей логики приложения, но я думаю, что ваши запросы могут быть сведены к чему-то такого рода:
# Find all the items where this user is the "user"
user_items = items.filter(user_item_rel_set__user=u)
# Find all the items where this user is the "buyer"
buyer_items = items.filter(user_item_rel_set__buyer=u)
Я не совсем понимаю, почему вы назначаете эти значения равны «t.price» в цикле или я буду расширять этот код.
Если это не помогает вашей работе, я рекомендую dumping your SQL queries to the console, чтобы вы могли точно видеть, что происходит за ORM. В логике, подобной этому, для получения вашего расчета не должно быть больше нескольких операторов SQL.
Кроме того, как правило, плохая идея использовать типы данных с плавающей точкой (float) в любом месте в непосредственной близости от денежной ценности. Типы данных с плавающей запятой, как правило, предназначены для научных приложений, где производительность важнее точности. Если вы имеете дело с деньгами, точность почти всегда более важна, чем производительность, поэтому вы используете тип данных, способный к точному представлению, например, decimal.Decimal везде.
Редактировать
Учитывая замечания, я рекомендую начать свой запрос с «отношения» объект вместо пункта. Так как ваш образец не сказать мне имя этого класса, я буду считать, что называется UserItem:
from django.db.models import Q
from decimal import Decimal
price = Decimal('0')
# Get all UserItems where this user is the user or buyer
interesting_items = UserItem.objects.filter((Q(user=u) | Q(buyer=u)))
for ii in interesting_items:
if ii.user == u:
price += ii.payment_amount
elif ii.buyer == u:
price -= ii.payment_amount
else:
assert False, "Oops, this shouldn't happen"
# Do something with 'price'...
Джанго «Q» объект позволяет получить немного больше зернистый с запросами. Если вам нужно фильтровать на основе какого-либо атрибута элемента, бросьте туда тоже.
Часть, которая все еще меня смущает в ваших примерах, почему вы назначаете «цену» объекту объекта, когда ясно, что многие пользователи будут делиться этим предметом.
Edit 2
Вы также можете использовать aggregation API позволить СУБД вычислить сумму, если это все, что вас интересует:
from django.db.models import Sum
buyer_price = UserItem.objects.filter(item=i, user=u).aggregate(
Sum('payment_amount'))['payment_amount__sum']
Так товара имеет цену, и его М2М отношения (user_item_rel), сколько пользователь заплатил за этот элемент. У меня есть список элементов, в которых задействован пользователь (именно тот код, который у вас есть), и я пытаюсь получить, сколько пользователь заплатил за каждый элемент, хотя я не могу этого сделать, не забивая базу данных для каждого отдельного элемента , – victor
Итак, поле «payment_amount» хранится в объекте отношений между пользователем и элементом? Я предполагаю, что отношение m2m имеет свою собственную модель? –
Да, это так. – victor