相关疑难解决方法(0)

namedtuple和可选关键字参数的默认值

我正在尝试将一个冗长的空洞"数据"类转换为一个命名元组.我的班级目前看起来像这样:

class Node(object):
    def __init__(self, val, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right
Run Code Online (Sandbox Code Playgroud)

转换为namedtuple它后看起来像:

from collections import namedtuple
Node = namedtuple('Node', 'val left right')
Run Code Online (Sandbox Code Playgroud)

但这里有一个问题.我的原始类允许我传入一个值,并使用命名/关键字参数的默认值来处理默认值.就像是:

class BinaryTree(object):
    def __init__(self, val):
        self.root = Node(val)
Run Code Online (Sandbox Code Playgroud)

但是这对我重构的名为元组的情况不起作用,因为它希望我传递所有字段.当然,我可以代替的出现Node(val)Node(val, None, None),但它不是我的胃口.

所以确实存在着一个很好的技巧,它可以使我重新写成功无需添加大量的代码复杂度(元编程),或者我应该只吞下药丸,并与"查找和替换"继续前进?:)

python default-value optional-arguments namedtuple

265
推荐指数
11
解决办法
9万
查看次数

如何在python中从变量参数(kwargs)设置类属性

假设我有一个带有构造函数(或其他函数)的类,它接受可变数量的参数,然后有条件地将它们设置为类属性.

我可以手动设置它们,但似乎变量参数在python中很常见,应该有一个共同的习惯用法.但我不确定如何动态地这样做.

我有一个使用eval的例子,但这几乎不安全.我想知道这样做的正确方法 - 也许是lambda?

class Foo:
    def setAllManually(self, a=None, b=None, c=None):
        if a!=None: 
            self.a = a
        if b!=None:
            self.b = b
        if c!=None:
            self.c = c
    def setAllWithEval(self, **kwargs):
        for key in **kwargs:
            if kwargs[param] != None
                eval("self." + key + "=" + kwargs[param])
Run Code Online (Sandbox Code Playgroud)

python

93
推荐指数
5
解决办法
7万
查看次数

使用Python类作为数据容器

有时将相关数据聚集在一起是有意义的.我倾向于用dict这样做,例如,

self.group = dict(a=1, b=2, c=3)
print self.group['a']
Run Code Online (Sandbox Code Playgroud)

我的一位同事更喜欢创建一个班级

class groupClass(object):
    def __init__(a, b, c):
        self.a = a
        self.b = b
        self.c = c
self.group = groupClass(1, 2, 3)
print self.group.a
Run Code Online (Sandbox Code Playgroud)

请注意,我们没有定义任何类方法.

我喜欢使用dict,因为我喜欢最小化代码行数.我的同事认为如果使用类,代码更具可读性,并且将来更容易向类中添加方法.

你更喜欢哪个?为什么?

python struct dictionary class

48
推荐指数
8
解决办法
5万
查看次数

Python:扩展预定义的命名元组

我有以下命名的元组:

from collections import namedtuple
ReadElement = namedtuple('ReadElement', 'address value')
Run Code Online (Sandbox Code Playgroud)

然后我想要以下内容:

LookupElement = namedtuple('LookupElement', 'address value lookups')
Run Code Online (Sandbox Code Playgroud)

两个命名元组之间存在重复,如何将ReadElement子类化为包含其他字段?

class LookupElement(ReadElement):
    def __new__(self, address, value, lookups):
        self = super(LookupElement, self).__new__(address, value)
        l = list(self)
        l.append(lookups)
        return tuple(l)
Run Code Online (Sandbox Code Playgroud)

然而,在语句中创建了元组,如果我将self修改为列表,我将丢失类型信息,我该如何避免这种情况?

python namedtuple python-2.7

19
推荐指数
2
解决办法
9877
查看次数

数据类与typing.NamedTuple主要用例

长话短说

PEP-557引入了数据类到Python标准库,基本上可以填补因为同样的作用collections.namedtupletyping.NamedTuple.现在我想知道如何分离使用namedtuple仍然是更好的解决方案的用例.

数据类优于NamedTuple

当然,dataclass如果我们需要,所有的功劳都归功于:

  • 可变对象
  • 继承支持
  • property 装饰器,可管理的属性
  • 生成的方法定义开箱即用或可自定义的方法定义

在同一个PEP中简要解释了数据类的优点:为什么不使用namedtuple.

问:在哪些情况下,namedtuple仍然是更好的选择?

但是对于namedtuples这个相反的问题怎么样:为什么不使用dataclass呢?我想从性能的角度来看,名字元组可能更好,但尚未确认.

让我们考虑以下情况:

我们将页面维度存储在一个小容器中,该容器具有静态定义的字段,类型提示和命名访问.不需要进一步散列,比较等.

NamedTuple方法:

from typing import NamedTuple

PageDimensions = NamedTuple("PageDimensions", [('width', int), ('height', int)])
Run Code Online (Sandbox Code Playgroud)

DataClass方法:

from dataclasses import dataclass

@dataclass
class PageDimensions:
    width: int
    height: int
Run Code Online (Sandbox Code Playgroud)

哪种解决方案更可取,为什么?

PS这个问题不是以任何方式重复那个问题,因为我在这里询问是哪个命名元组更好,而不是区别(我在询问之前检查了文档和来源)

python pep namedtuple python-3.7 python-dataclasses

19
推荐指数
6
解决办法
3535
查看次数

为了类型检查而将NamedTuple子类化的方法

我有几个分享一些字段的命名元组.我有一个接受这些元组的函数,并保证只与共享字段交互.我想在mypy中检查这样的代码.

代码的一个例子是:

from typing import NamedTuple

class Base(NamedTuple):
    x: int
    y: int


class BaseExtended(NamedTuple):
    x: int
    y: int
    z: str

def DoSomething(tuple: Base):
    return tuple.x + tuple.y

base = Base(3, 4)
base_extended = BaseExtended(5, 6, 'foo')

DoSomething(base)
DoSomething(base_extended)
Run Code Online (Sandbox Code Playgroud)

当我在这段代码上运行mypy时,我得到一个可预测的错误:

mypy_example.py:20:错误:"DoSomething"的参数1具有不兼容的类型"BaseExtended"; 预期"基地"

有没有办法构建我的代码并保持mypy typechecking?我不能从Base继承BaseExtended,因为NamedTuple继承实现中存在一个错误:

https://github.com/python/typing/issues/427

我也不想使用一个丑陋的"Union [Base,BaseExtended]",因为当我尝试对一个List进行类型检查时会出现这种情况,因为"List [Union [Base,BaseExtended]]"不等于"List [BaseExtended] ]"由于关于变体/协变类型的一些mypy魔术:

https://github.com/python/mypy/issues/3351

我应该放弃这个想法吗?

python typing namedtuple mypy

13
推荐指数
1
解决办法
2367
查看次数

是否可以在数据类中使用*args?

我最近开始使用数据类,它们将是3.7的一个很好的补充.我很好奇是否或如何使用数据类重新创建此类的相同功能.

class Nav(object):
    def __init__(self, name:str, menu, page, *submenus):
        self.name = name
        self.menu = menu
        self.page = page
        self.submenus = submenus

foo = Nav("name", "menu", "page")
Run Code Online (Sandbox Code Playgroud)

这不起作用.提出例外TypeError: __init__() missing 1 required positional argument: 'submenus'

@dataclass
class Nav(object):
    name:str
    menu: Any
    page: Any
    submenus: tuple

foo = Nav("name", "menu", "page")
Run Code Online (Sandbox Code Playgroud)

我假设这是因为该类没有指令来解析参数. 有没有办法指示数据类装饰器需要解压缩子菜单?

python python-3.x python-dataclasses

13
推荐指数
1
解决办法
860
查看次数

如何使python数据类可哈希化?

假设我在python3中有一个数据类。我希望能够哈希和排序这些对象。

我只希望它们在ID上排序/散列。

我在文档中看到,我可以只实现__hash__,但我想让datacalses为我完成工作,因为它们旨在处理此问题。

from dataclasses import dataclass, field

@dataclass(eq=True, order=True)
class Category:
    id: str = field(compare=True)
    name: str = field(default="set this in post_init", compare=False)

a = sorted(list(set([ Category(id='x'), Category(id='y')])))

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: unhashable type: 'Category'
Run Code Online (Sandbox Code Playgroud)

python hash python-3.x python-dataclasses

13
推荐指数
3
解决办法
3135
查看次数

Python - 函数输出?

我有一个非常基本的问题.

假设我调用一个函数,例如,

def foo():
    x = 'hello world'
Run Code Online (Sandbox Code Playgroud)

如何让函数以这样的方式返回x,我可以将它用作另一个函数的输入或者在程序体内使用变量?

当我使用return并在另一个函数中调用该变量时,我得到一个NameError.

python function

10
推荐指数
2
解决办法
7万
查看次数

在Python中创建嵌套的数据类对象

我有一个dataclass对象,其中包含嵌套的数据类对象.但是,当我创建主对象时,嵌套对象变成了字典:

@dataclass
class One:
    f_one: int

@dataclass
class One:
    f_one: int
    f_two: str

@dataclass
class Two:
    f_three: str
    f_four: One


data = {'f_three': 'three', 'f_four': {'f_one': 1, 'f_two': 'two'}}

two = Two(**data)

two
Two(f_three='three', f_four={'f_one': 1, 'f_two': 'two'})

obj = {'f_three': 'three', 'f_four': One(**{'f_one': 1, 'f_two': 'two'})}

two_2 = Two(**data)

two_2
Two(f_three='three', f_four={'f_one': 1, 'f_two': 'two'})
Run Code Online (Sandbox Code Playgroud)

正如您所看到的,我试图将所有数据作为字典传递,但我没有得到预期的结果.然后我尝试首先构造嵌套对象并将其传递给对象构造函数,但我得到了相同的结果.

理想情况下,我想构建我的对象来得到这样的东西:

Two(f_three='three', f_four=One(f_one=1, f_two='two'))
Run Code Online (Sandbox Code Playgroud)

除了手动将嵌套字典转换为相应的数据类对象,每当访问对象属性时,有没有办法实现其他目的?

提前致谢.

python serialization nested object python-dataclasses

6
推荐指数
5
解决办法
4441
查看次数

Python mypy无法从union返回类型推断出类型

这是示例代码

from typing import Dict, Union, Tuple


def select_range(data: Dict[str, Union[str, int]]) -> Tuple[int, int]:
    if data['start'] and data['end']:
        return data['start'], data['end']
    return 1, 1

select_range({})
Run Code Online (Sandbox Code Playgroud)

Mypy输出:

mypy different_return.py
different_return.py:6: error: Incompatible return value type (got 
"Tuple[Union[str, int], Union[str, int]]", expected "Tuple[int, int]")
Run Code Online (Sandbox Code Playgroud)

即使其中一个字典值是int,mypy也无法推断出这一点.

python static-typing mypy

4
推荐指数
1
解决办法
842
查看次数

DataClass 是否适合替换字典?

我在代码中经常使用字典作为数据结构。而不是Tuple像 Python 允许的那样返回几个值:

def do_smth():
  [...]
  return val1, val2, val3
Run Code Online (Sandbox Code Playgroud)

我更喜欢使用具有命名键优势的字典。但是对于复杂的嵌套字典,很难在其中导航。几年前我用 JS 编码时,我也喜欢字典,因为我可以像调用子部分一样thing.stuff.foo,IDE 帮助我处理结构。

我刚刚发现了DataClasspython 中的新内容,除了替换字典之外,我不确定这是什么原因?对于我所阅读的内容,DataClass内部无法包含函数,并且其参数的初始化已简化。

我想对此发表评论,你如何使用DataClass, 或关于 python 中的字典。

python dictionary python-dataclasses

3
推荐指数
1
解决办法
5950
查看次数

具有固定 .keys() 内容和可变参数的 Python 字典

我正在尝试从文本文件中读取大量数据到字典中,并且我犯了几个小错别字,最终导致创建新的键/值对并破坏程序(这可能很烦人和痛苦)调试)。

这让我想知道是否有一种方法可以创建一个字典,在初始声明之后不能添加或删除任何键。我觉得这是必然存在的东西,但我找不到它的例子;有谁知道有什么符合要求的吗?

def change_key(dictionary, key, new_value):
    a = dictionary.__len__()
    dictionary[key] = new_value
    if dictionary.__len__() != a:
        raise ValueError("new key added")
Run Code Online (Sandbox Code Playgroud)

我正在寻找的是上面代码的更优雅的实现,即:

  1. 不是一大堆乱七八糟的代码

  2. 能够处理诸如附加到嵌套列表或添加到嵌套字典之类的事情

  3. 相当有效

python python-3.9

2
推荐指数
1
解决办法
755
查看次数