[英]Django parameters read in wrong order
我有以下模型:
class Work(models.Model):
title = models.CharField(max_length=30)
amount = models.PositiveIntegerField()
percent = models.FloatField(validators=[MaxValueValidator
(100),MinValueValidator(0)])
drop = models.PositiveIntegerField(default=0)
assignments = models.ManyToManyField(Assignment)
但是當我創建一些“作品”時,它的行為很奇怪:
In [6]: homework = Work("homework",12,15)
In [7]: homework.save()
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
...
#lots and lots of stuff...I will post the extend at the bottom
...
ValueError: invalid literal for int() with base 10: 'homework'
當第一個參數需要CharField時,為什么讀取第一個參數應該為int?
我認為我說的很有道理。 homework.title
應該是“ homework”, homework.amount
應該是12, homework.percent
應該是15, homework.drop
應該是默認值:0。
有人可以解釋為什么會出現此錯誤以及如何解決該錯誤。 提前致謝。
In [6]: homework = Work("homework",12,15)
In [7]: homework.save()
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/core/management/commands/shell.pyc in <module>()
----> 1 homework.save()
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/base.pyc in save(self, force_insert, force_update, using, update_fields)
544
545 self.save_base(using=using, force_insert=force_insert,
--> 546 force_update=force_update, update_fields=update_fields)
547 save.alters_data = True
548
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/base.pyc in save_base(self, raw, cls, origin, force_insert, force_update, using, update_fields)
620 # no force_insert)
621 if ((force_update or update_fields) or (not force_insert and
--> 622 manager.using(using).filter(pk=pk_val).exists())):
623 if force_update or non_pks:
624 values = [(f, None, (raw and getattr(self, f.attname) or f.pre_save(self, False))) for f in non_pks]
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/query.pyc in filter(self, *args, **kwargs)
665 set.
666 """
--> 667 return self._filter_or_exclude(False, *args, **kwargs)
668
669 def exclude(self, *args, **kwargs):
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/query.pyc in _filter_or_exclude(self, negate, *args, **kwargs)
683 clone.query.add_q(~Q(*args, **kwargs))
684 else:
--> 685 clone.query.add_q(Q(*args, **kwargs))
686 return clone
687
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/sql/query.pyc in add_q(self, q_object, used_aliases, force_having)
1257 else:
1258 self.add_filter(child, connector, q_object.negated,
-> 1259 can_reuse=used_aliases, force_having=force_having)
1260 if force_having:
1261 self.having.end_subtree()
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/sql/query.pyc in add_filter(self, filter_expr, connector, negate, trim, can_reuse, process_extras, force_having)
1188 else:
1189 self.where.add((Constraint(alias, col, field), lookup_type, value),
-> 1190 connector)
1191
1192 if negate:
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/sql/where.pyc in add(self, data, connector)
69
70 if hasattr(obj, "prepare"):
---> 71 value = obj.prepare(lookup_type, value)
72
73 super(WhereNode, self).add(
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/sql/where.pyc in prepare(self, lookup_type, value)
337 def prepare(self, lookup_type, value):
338 if self.field:
--> 339 return self.field.get_prep_lookup(lookup_type, value)
340 return value
341
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/fields/__init__.pyc in get_prep_lookup(self, lookup_type, value)
320 return value
321 elif lookup_type in ('exact', 'gt', 'gte', 'lt', 'lte'):
--> 322 return self.get_prep_value(value)
323 elif lookup_type in ('range', 'in'):
324 return [self.get_prep_value(v) for v in value]
/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/django/db/models/fields/__init__.pyc in get_prep_value(self, value)
553 if value is None:
554 return None
--> 555 return int(value)
556
557 def contribute_to_class(self, cls, name):
ValueError: invalid literal for int() with base 10: 'homework'
在工作表中創建新記錄時,需要使用關鍵字參數。
homework = Work(title = "homework", amount = 12, drop = 15)
homework.save()
指定參數的順序無關緊要。 如果為函數指定了關鍵字,例如
def attributes(self, pk='', title='', amount=''):
...
然后,您可以按順序指定參數而不使用關鍵字。 但是,Django模型不這樣做,因為它們無法猜測您的字段名稱是什么。 他們會像這樣實現更多
def attributes(self, **kwargs):
...
其中kwargs將是所有指定關鍵字參數的字典。 然后,Django模型將根據您在其中傳遞的任何關鍵字參數來更新數據庫。
不是第一個參數應該是一個int。 它應該是一個charfield,帶有數字的內容。 Django嘗試將其轉換為int,但是由於文本是homework
-這不是有效數字,因此失敗。 第一個參數應為id
,整數或數字字符串。
您必須指定關鍵字:
homework = Work(title = "homework", amount = 12, drop = 15)
為什么? 因為默認的第一個參數不是標題或用戶定義的任何東西,所以它是id。 因此,如果要跳過id(它將由Django自動設置)以及其他可能生成的其他一些參數,則必須指定關鍵字。
每個django模型都有一個自動主鍵,其默認名稱是id
。 當使用Work(“ homework”,12,15)初始化Work模型時,您要將“ homework”字符串傳遞給id字段。
from product.models import Work
homework = Work("homework",12,15)
print homework.id
#outputs 'homework'
在django doc中,我也找不到任何能保證Model.__init__
args順序與字段定義順序相同的詞(由於元類 ,順序可能不同)。 因此,您應該使用名稱參數(kwargs)。
您可以通過簡單地實現
Work.objects.create(title="homework", amount=12, drop=15)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.