交换两个关键字参数的位置会引发错误

发布于 2024-08-21 02:14:10 字数 935 浏览 8 评论 0原文

我有一个奇怪的问题。我知道在Python中,kwargs跟随args,所以我检查了这一点,这不是问题。问题是这样的:

很好:

def __init__(self,sample_rate, label=u"", data=[] ):

TypeError: __init__() got multiple value for 关键字参数 'data':

def __init__(self, Sample_rate, data=[], label=u""):

抛出错误的调用行如下所示:

def __getslice__(self, start, stop):
    return Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))

完整代码:

class Channel(list):
  sample_rate = 0

  def __init__(self, sample_rate, data=[], label=u"" ):
     list.__init__(self,data)
     self.sample_rate = sample_rate
     self.label = label

  @property
  def nyquist_rate(self):
      return float(self.sample_rate) / 2.0

  def __getslice__(self, start, stop):
      return Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))

谢谢!

I have an odd problem. I know that in Python, kwargs follow args, so I checked for that and it's not the problem. What is the problem is this:

Fine:

def __init__(self, sample_rate, label=u"", data=[] ):

TypeError: __init__() got multiple values for keyword argument 'data':

def __init__(self, sample_rate, data=[], label=u""):

The calling line that throws the error looks like this:

def __getslice__(self, start, stop):
    return Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))

The full code:

class Channel(list):
  sample_rate = 0

  def __init__(self, sample_rate, data=[], label=u"" ):
     list.__init__(self,data)
     self.sample_rate = sample_rate
     self.label = label

  @property
  def nyquist_rate(self):
      return float(self.sample_rate) / 2.0

  def __getslice__(self, start, stop):
      return Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))

Thank you!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

小猫一只 2024-08-28 02:14:10

在第二个版本 (def __init__(self,sample_rate, data=[], label=u""):) 中,第二个位置参数(调用时,这意味着不计算 self< /code>) 是 data,但在 __getslice__ 中,您传递的第二个参数是 label。因此,您应该保留 label 作为第二个参数,或者将函数调用更改为:

return Channel(self.sample_rate, label=self.label, data=list.__getslice__(self,start,stop))

In the second version (def __init__(self, sample_rate, data=[], label=u""):), the second positional argument (when called, that means not counting self) is data, but in __getslice__, the second argument that you pass is label. So you should either keep label as the second argument, or change the function call to this:

return Channel(self.sample_rate, label=self.label, data=list.__getslice__(self,start,stop))
瀞厅☆埖开 2024-08-28 02:14:10

您正在调用代码,请

Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))

注意第二个参数没有关键字,因此解释器假定这是 data 参数(因为这是它们在函数中定义的顺序)。如果添加 label= 应该可以解决它。

但是,您的代码中有一个更重要的错误:切勿使用 [] 作为默认值。原因是该代码是在函数定义时评估的。每次您在不带 data 参数的情况下调用此代码时,您将获得与默认值相同的列表。第一次之后它可能不会是空的!对于所有可变数据类型都是如此。正确的方法是使用 None 作为默认值,并在函数内部(每次运行的代码)初始化一个新的 [](如果参数值为 None)。
(这个 gocha 也被 David Goodger 很好地解释了,在 默认参数值

You are calling the code with

Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))

Note that the second parameter has no keyword, so the interpreter assumes this is the data parameter (because that's the order they are defined in the function). If you add label= it should solve it.

But, you have a more important error in your code: Never use [] as a default value. The reason is this code is evaluated at function definition time. every time you call this code with no data parameter, you'll get the same list as a default value. and it might not be empty after the first time! This is true for all mutable datatypes. The correct way to do this, is to use None as a default value and inside the function (code that runs each time) init a new [], if the parameter value is None.
(This gocha is also explained well by David Goodger, in Default Parameter Values)

你如我软肋 2024-08-28 02:14:10

问题在于,在调用代码中,有两个位置参数:

return Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))
#              sample_rate (pos) data (pos)  data (kw)

在 Python 2.x 中,函数定义中的位置参数和关键字参数之间没有区别。调用函数时,函数调用中的位置参数用于从左到右填充参数,然后绑定所有关键字参数。在您的情况下,data 同时受到位置参数和关键字参数的绑定。它在另一种情况下有效,因为第二个位置参数用于标签,而数据仅获取关键字参数。

The problem is that in your calling code, you have two positional arguments:

return Channel(self.sample_rate, self.label, data=list.__getslice__(self,start,stop))
#              sample_rate (pos) data (pos)  data (kw)

In Python 2.x, there is no distinction between positional and keyword arguments in the function definition. When a function is called, positional arguments from the function invocation are used to fill arguments left to right, then all keyword arguments are bound. In your case, data is bound both by a positional and a keyword arguments. It works in the other case because then the second positional argument is used for label, and data only gets the keyword argument.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文