Как я могу вычислить результат из связанных моделей в django

class Function(models.Model):
    name = models.CharField(max_length=200)
    def __str__(self):
        return str(self.name)

class Fractions(models.Model):
  fraction = models.DecimalField( max_digits = 5,decimal_places = 2)
  def __str__(self):
    return str(self.fraction)

 class Project(models.Model):
    func= models.ForeignKey(Function, on_delete=models.SET_NULL, null=True)
    fraction= models.ForeignKey(Fraction, on_delete=models.SET_NULL, null=True)
    ratio = models.IntegerField(max_lenght=200)

Что я пытаюсь сделать, если Function.name equals = "x" умножить конкретную Fractions.fraction на 4 и присвоить результат соотношению

Предполагая, что Function имена уникальны:

project = Project.objects.get(func__name='x')
return project.fraction.fraction * project.ratio

Если ratio полностью зависит от Function и Fraction, то хранить это не имеет особого смысла. Тогда вы можете просто реализовать это как свойство, например:

class Function(models.Model):
    name = models.CharField(max_length=200)

    def evaluate(self, x):
        if self.name == 'x':
            return 4 * x
        return x

    def __str__(self):
        return str(self.name)


class Fraction(models.Model):
    fraction = models.DecimalField(max_digits=5, decimal_places=2)

    def __str__(self):
        return str(self.fraction)


class Project(models.Model):
    func = models.ForeignKey(Function, on_delete=models.SET_NULL, null=True)
    fraction = models.ForeignKey(Fraction, on_delete=models.SET_NULL, null=True)

    @property
    def ratio(self):
        if self.func is not None and self.fraction is not None:
            return self.func.evaluate(self.fraction.fraction)

Таким образом, он определит отношение, получив объект Function и вызвав .evaluate(…). В случае если имя x, он вернет значение, умноженное на четыре, в противном случае он вернет само значение.

В дополнение к другим ответам, вы можете использовать библиотеку операторов Питона для выполнения операций и вставки их в dict. Я бы предложил комбинировать это с choices на вашем поле имени - хотя обратите внимание, что выбор не может быть операторной функцией, а строковым значением.

import operator 

FUNCTIONS = {
    '+': operator.add,
    '-': operator.sub,
    '*': operator.mul,
    '/': operator.truediv
}

class Function(models.Model):
    name = models.CharField(max_length=200)

    def __str__(self):
        return str(self.name)

    def evaluate(self, a, b)
        op = FUNCTIONS.get(self.name)
        if op:
            return op(a, b)
        return None
Вернуться на верх