擴大我給你的答案評論,我試着寫一個查詢集你想要什麼,會做,但它似乎可以根據你的數據模型不。
您的數據模型實際上並未描述特定醫生治療特定患者的日期範圍。無論您如何編寫查詢,您正在編寫的查詢都會返回錯誤的結果。您目前所說的內容如下:
「如果患者死亡,那麼任何對該患者進行治療的醫生將被標記爲」負責「。 (責任可能不是這裏正確的詞,但你應該明白)。
現在,如果您只是將一個GP分配給is_main
給特定的患者,那麼以上方法都是正確的..但是您的數據模型並未強制執行此操作,並且可能容易出錯。特別是如果is_main
在患者死亡後改變。我將構建數據模型爲以下之一:
class GP(models.Model):
name = models.CharField(max_length=64)
class Patient(models.Model):
name = models.CharField(max_length=64)
class Death(models.Model):
current_gp = models.ForeignKey(GP)
patient = models.ForeignKey(Patient)
date = models.DateField()
class Consultation(models.Model):
gp = models.ForeignKey(GP)
patient = models.ForeignKey(Patient)
start_date = models.DateField()
end_date = models.DateField(blank=True, null=True)
或..
class GP(models.Model):
name = models.CharField(max_length=64)
class Patient(models.Model):
name = models.CharField(max_length=64)
class Death(models.Model):
patient = models.ForeignKey(Patient)
date = models.DateField()
class Consultation(models.Model):
gp = models.ForeignKey(GP)
patient = models.ForeignKey(Patient)
start_date = models.DateField()
end_date = models.DateField(blank=True, null=True)
第一結構具有允許非常好的疑問,這將是非常高性能的利益,在成本要求在患者死亡時輸入額外的信息。但是,Consultation
(以前的PatientGPLink)模型將具有推導此信息所需的所有信息。你也可以使Death.current_gp成爲一個ManyToManyField來支持多個GP負責病人。
第二個結構可以收集相同的信息,但需要日期時間過濾,這將加入另一個表,並使查詢更慢,更復雜。
如果您非常清楚維護is_main
字段,所有這些都是無關緊要的,因爲數據是正確的。但讓我告訴你如何查詢您的(可能)要更有效的方式從您的視圖的信息:
def my_view(request):
doctors = GP.objects.all()
periods = get_time_periods() # however it is you do this...
smallest_date = get_smallest_date(time_periods)
largest_date = get_largest_date(time_periods)
deaths = Death.objects.select_related(depth=1).filter(date__range=(smallest_date, largest_date))
# build the results table with initial count of 0 to account for all doctors
# {period: {doctor: count}}
results = dict((period,{doctor: 0}) for doctor in doctors for period in periods)
for death in deaths:
for period in time_periods: # I'm assuming this is a small range of values
if death.date > period['start_date'] and death.date < period['end_date']:
results[period][death.current_gp] += 1 # add a death to the count
然後,在你的模板,你有results
表的所有預先計算的信息:
<table>
{% for period, lookup in results.items %}
{% for doctor, deaths in lookup.items %}
<tr>
<td>{{ period }}</td>
<td>{{ doctor }}</td>
<td>{{ deaths }}</td>
</tr>
{% endfor %}
{% endfor %}
</table>
對於總共2個SQL查詢。這種方式有更多的手動處理,但計算結果應該比查詢數據庫num_doctors * num_timeperiods + 1倍更快,這是您當前正在執行的操作。
編輯:
,使其與當前的模型結構工作(如果你真的不能更改機型...),您合併與我你的答案,並與這是非常相似的視圖,結束了到我寫的原文。我將所有評論都刪掉,因爲他們會和上面一樣。我已將評論放在我改變原始視圖的地方。
def my_view(request):
doctors = GP.objects.all()
periods = get_time_periods()
smallest_date = get_smallest_date(time_periods)
largest_date = get_largest_date(time_periods)
# we make depth=3 so it spans via the PatientGPLink over to GP
deaths = Death.objects.select_related(depth=3).filter(date__range=(smallest_date, largest_date)).filter(patient__patientgplink__ismain=True)
results = dict((period,{doctor: 0}) for doctor in doctors for period in periods)
for death in deaths:
for period in time_periods:
if death.date > period['start_date'] and death.date < period['end_date']:
# and we change how we access the GP
results[period][death.patient.patientgplink.gp] += 1
仍然只有兩個查詢,儘管這些查詢更大(跨越多個表)。
你可以發佈醫生queryset的代碼嗎?和my_new_queryset?最終模型?謝謝 ! – jpic 2012-03-23 11:53:45
醫生是一個集合或一個集合(我還沒有做過)。我的新查詢集是我遇到的問題之一。 – 2012-03-23 11:59:34