在Python中冻结?

ker*_*ger 12 ruby python list freeze

我已经在Python中编程了一段时间,最近才开始在工作中使用Ruby.语言非常相似.但是,我刚刚遇到了一个Ruby功能,我不知道如何在Python中进行复制.这是Ruby的freeze方法.

irb(main):001:0> a = [1,2,3]
=> [1, 2, 3]
irb(main):002:0> a[1] = 'chicken'
=> "chicken"
irb(main):003:0> a.freeze
=> [1, "chicken", 3]
irb(main):004:0> a[1] = 'tuna'
TypeError: can't modify frozen array
        from (irb):4:in `[]='
        from (irb):4
Run Code Online (Sandbox Code Playgroud)

有没有办法在Python中模仿这个?

编辑:我意识到我觉得这只是为了列表; 在Ruby中,freeze是一个方法,Object所以你可以使任何对象不可变.我为这种困惑道歉.

Sil*_*ost 12

>>> a = [1,2,3]
>>> a[1] = 'chicken'
>>> a
[1, 'chicken', 3]
>>> a = tuple(a)
>>> a[1] = 'tuna'
Traceback (most recent call last):
  File "<pyshell#4>", line 1, in <module>
    a[1] = 'tuna'
TypeError: 'tuple' object does not support item assignment
Run Code Online (Sandbox Code Playgroud)

另外,参见 setvs. frozenset,bytearrayvs bytes.

数字,字符串本身是不可变的:

>>> a = 4
>>> id(a)
505408920
>>> a = 42        # different object
>>> id(a)
505409528
Run Code Online (Sandbox Code Playgroud)

  • 我知道元组,我编辑了我的原始问题,以澄清我在谈论所有对象.我反对你声称在Python中冻结任何对象是微不足道的.至少它不像'obj.freeze()`那样微不足道,除非有一些我不知道的东西. (3认同)
  • @kerkeslager:你已经接受了一个完全符合我的代码所做的答案,只是以一种尴尬的非本地方式.你当然不能在python中冻结内置对象,但这不是你要问的是什么? (2认同)

Nic*_*k T 11

你总是可以子类化list并添加"冻结"标志,它会阻止__setitem__做任何事情:

class freezablelist(list):
    def __init__(self,*args,**kwargs):
        list.__init__(self, *args)
        self.frozen = kwargs.get('frozen', False)

    def __setitem__(self, i, y):
        if self.frozen:
            raise TypeError("can't modify frozen list")
        return list.__setitem__(self, i, y)

    def __setslice__(self, i, j, y):
        if self.frozen:
            raise TypeError("can't modify frozen list")
        return list.__setslice__(self, i, j, y)

    def freeze(self):
        self.frozen = True

    def thaw(self):
        self.frozen = False
Run Code Online (Sandbox Code Playgroud)

然后玩它:

>>> from freeze import freezablelist as fl
>>> a = fl([1,2,3])
>>> a[1] = 'chicken'
>>> a.freeze()
>>> a[1] = 'tuna'
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "freeze.py", line 10, in __setitem__
    raise TypeError("can't modify frozen list")
TypeError: can't modify frozen list
>>> a[1:1] = 'tuna'
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "freeze.py", line 16, in __setslice__
    raise TypeError("can't modify frozen list")
TypeError: can't modify frozen list
>>>
Run Code Online (Sandbox Code Playgroud)