Django ссылка на несколько таблиц - PullRequest
1 голос
/ 19 мая 2019

У меня есть четыре модели следующим образом:

class deals_view(models.Model):

    deal = models.ForeignKey(dealsModel, on_delete=models.CASCADE, related_name='deal_view')
    client = models.ForeignKey(client_profileModel, on_delete=models.CASCADE)
    client_ip = models.GenericIPAddressField(protocol='both')
    date_added = models.DateField(auto_now_add=True)


class client_profile(models.Model):

    GENDER_NAME = (
        ('M', 'Male'),
        ('F', 'Female'),
        ('O', 'Others')
    )

    user = models.ForeignKey(User, unique=True, on_delete=models.CASCADE)
    gender = models.CharField(max_length=1, choices=GENDER_NAME, null=True)
    address = models.CharField(max_length=100, null=True)
    dob = models.DateField(null=True)

class deals(models.Model):

    GENDER_NAME = (
        ('M', 'Male'),
        ('F', 'Female'),
        ('O', 'Others'),
        ('A', 'All'),
    )

    AGE_RANGE = (
        ('A1', '18-25'),
        ('A2', '25-40'),
        ('A3', '40-55'),
        ('A4', '55-100'),
        ('A5', '18-100'),
        ('AL', '13-100'),
        ('T1', '13-18')
    )

    store = models.ForeignKey(storesModel, on_delete=models.CASCADE, related_name='deals_store')
    title = models.CharField(max_length=30)
    description = models.CharField(max_length=160)
    price = models.DecimalField(max_digits=6, decimal_places=2)
    category = models.ForeignKey(categoriesModel, on_delete=models.PROTECT)
    targeted_gender = models.CharField(max_length=1, choices=GENDER_NAME)
    targeted_age = models.CharField(max_length=2, choices=AGE_RANGE)
    is_active = models.BooleanField(default=False)
    created_date = models.DateField(auto_now_add=True)
    expiry_date = models.DateField(default=(dt.now() + td(days=30)))


class stores(models.Model):
    user = models.ForeignKey(User, on_delete=models.CASCADE)
    name = models.CharField(max_length=50, unique=True)
    about = models.CharField(max_length=300)
    company_name = models.CharField(max_length=100)

Я хочу перечислить все сделки за текущий месяц и соответствующее количество просмотров по полу.

до сих пор я пробовал следующее; я могу получить всю информацию, но, похоже, у меня есть несколько попаданий в базу данных:

self.storeObj = storesModel.objects.prefetch_related('deals_store').get(id=storeid)
self.deals_store = self.storeObj.deals_store

segmentedInfo = self.deals_store.all().prefetch_related('deal_view').filter(deal_view__date_added__range=((datetime.today() - timedelta(days=30)), datetime.now())).distinct()
            for seg in segmentedInfo:
                for x in seg.deal_view.select_related('client').distinct():
                    print(x.client.gender)

Можно ли как-нибудь оптимизировать свои запросы, чтобы получить количество просмотров по полу для сделки определенного магазина?

1 Ответ

1 голос
/ 19 мая 2019

Да, мы можем выполнить некоторую фильтрацию в связанной модели client_profile, а затем использовать .annotate(..) для подсчета количества различных идентификаторов.

from django.db.models import Count

client_profile.objects.filter(
    deals_view__deal__store_id=storeid,
    deals_view__date_added__range=(datetime.today()-timedelta(days=30), datetime.now())
).values('gender').annotate(
    <b>n=Count('id', distinct=True)</b>
).order_by('gender')

Это приведет к QuerySetкоторый содержит словари с полом и числом client_profile s, например:

<QuerySet [
    {'gender': 'M', 'n': 1425},
    {'gender': 'M', 'n': 1302},
    {'gender': 'O', 'n': 173}
]>

Если нет client_profile s с данным полом, которые видели бы сделку, то это не часть QuerySet.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...