Django Переоценка переменных в шаблоне
Допустим, в своих моделях я использую:
def Model1(models.Model):
model2 = models.ForeignKey(Model2)
def Model2(models.Model):
model3 = models.ForeignKey(Model3)
def Model3(models.Model):
code1 = models.CharField(max_length=150)
code2 = models.CharField(max_length=150)
code3 = models.CharField(max_length=150)
code4 = models.CharField(max_length=150)
code5 = models.CharField(max_length=150)
code6 = models.CharField(max_length=150)
code7 = models.CharField(max_length=150)
А в шаблоне:
<td> {{ model1.model2.model3.code1 }} </td>
<td> {{ model1.model2.model3.code2 }} </td>
<td> {{ model1.model2.model3.code3 }} </td>
<td> {{ model1.model2.model3.code4 }} </td>
<td> {{ model1.model2.model3.code5 }} </td>
<td> {{ model1.model2.model3.code6 }} </td>
<td> {{ model1.model2.model3.code7 }} </td>
и для сравнения:
{% with col=model1.model2.model3 %}
<td> {{ col.code1 }} </td>
<td> {{ col.code2 }} </td>
<td> {{ col.code3 }} </td>
<td> {{ col.code4 }} </td>
<td> {{ col.code5 }} </td>
<td> {{ col.code6 }} </td>
<td> {{ col.code7 }} </td>
{% endwith %}
В представлении я не использую select_related.
Мои вопросы следующие:
- Для первого кода означает ли это, что
model1.model2.model3
будет запрошен Django 7 раз? - Для второго кода, может ли использование with
col=model1.model2.model3
ускорить отрисовку шаблона, так как запросmodel1.model2.model3
осуществляется только один раз из блока{% with %}
, и только получение переменных из col? - Есть ли альтернативы обоим этим подходам?
В настоящее время моя SQL-таблица состоит из менее чем 1000 строк, поэтому проблемы с производительностью могут быть не видны. Но меня беспокоит вопрос, когда SQL-таблица будет достаточно большой и потребуется много оптимизации запроса.
- Да, Если вы не кэшируете результат запроса или любой другой пользовательский менеджер или ..., Django ORM будет выполнять вопрос каждый раз, когда вы его вызываете, для получения дополнительной информации об этом вы можете прочитать "When QuerySets are evaluated" в официальной документации.
- Это лучший способ, чем первый, потому что, как вы сказали, вы обращаетесь к базе данных только один раз и сохраняете результат, чтобы использовать его снова и снова.
- Зависит от того, что вы хотите сделать, если это не должно быть в реальном времени, вы можете использовать кэш, или вы можете написать функцию в model1 и вернуть то, что вы хотите от этой функции, затем вы можете сделать больше в ней (учитывая документацию, которую я упоминал ранее, чтобы сделать то, что вы хотите только в одном запросе)