django在QuerySet上使用len()时给出TypeError

joa*_*ofe 4 python django

我正在编写一个非常简单的应用程序来存储足球比赛的结果,我遇到了以下问题.运行其中一个单元测试时,以下代码:

listCompetition = Competition.objects.filter(compId=competitionId)
if len(listCompetition) == 0:
   #some code here
else:
   #some code here
Run Code Online (Sandbox Code Playgroud)

给出以下错误:

File "C:\Users\admin\workspace\project\src\bla\bla\module.py", line 222, in getMatches
   if len(listCompetition) == 0:
File "C:\Python27\lib\site-packages\django\db\models\query.py", line 82, in __len__
   self._result_cache = list(self.iterator())
File "C:\Python27\lib\site-packages\django\db\models\query.py", line 286, in iterator
   obj = model(*row[index_start:aggregate_start])
TypeError: __init__() takes exactly 3 arguments (4 given)
Run Code Online (Sandbox Code Playgroud)

但是,如果我用第一行代码替换:

listCompetition = list(Competition.objects.filter(compId=competitionId))
Run Code Online (Sandbox Code Playgroud)

然后它工作得很好.为什么它会以这种奇怪的方式表现?如果我在类比赛的构造函数中只定义了两个参数,那么Django如何传递4个参数?如果有帮助,这里是类竞赛的模型定义:

class Competicion(MultiName):
   def __init__(self, canonicalName, compId):
      super(Competition, self).__init__(canonicalName, compId)

class MultiName(models.Model):
   entId = models.CharField(null=True, max_length=25); 
   canonicalName = models.CharField(max_length=50, primary_key=True);

   def __init__(self, canonicalName, entId=None):
      super(MultiName, self).__init__()
      self.canonicalName = canonicalName;
      self.entId = entId;
Run Code Online (Sandbox Code Playgroud)

非常感谢你.

Elf*_*erg 6

简单:在第一种情况下,您将返回一个queryset对象,而不是列表.查询集是迭代器.列表对象也是迭代器,但迭代器不是列表.

Django这样做是为了优化内存和性能:数据库保留集合,Django每次从请求集中请求一个对象时,一次读取一个项目.使用list()导致Django读取整个响应并将其打包到列表对象中.如果返回集非常大,则可能会出现问题.

要了解查询集的大小,请使用该Queryset.count()方法.


Leo*_*opd 5

代替

if len(listCompetition) == 0:
Run Code Online (Sandbox Code Playgroud)

if listCompetition.count() == 0:
Run Code Online (Sandbox Code Playgroud)

也许

if not listCompetition.exists():
Run Code Online (Sandbox Code Playgroud)


bra*_*ers 3

它被破坏了,因为当您覆盖__init__. 你为什么还要实施__init__?您正在实施的是\xe2\x80\xa6 已经实施的。

\n\n

您似乎对如何使用 Django 做出了毫无根据的假设。我建议您在继续之前阅读本教程

\n\n

要修复您的代码,请将其更改为以下内容:

\n\n
class Competition(MultiName):\n    def __init__(self, *args, **kwargs):\n        if "compId" in kwargs:\n            kwargs["entId"] = kwargs.pop("compId")\n        super(Competition, self).__init__(*args, **kwargs)\n\nclass MultiName(models.Model):\n    entId = models.CharField(null=True, max_length=25); \n    canonicalName = models.CharField(max_length=50, primary_key=True);\n
Run Code Online (Sandbox Code Playgroud)\n\n

有很多很棒的模型文档涵盖了这些内容。

\n