불변 유형이 무엇인지 혼란 스럽습니다. 필자의 float책에서 이러한 유형의 예제를 사용 하면 객체가 변경 불가능한 것으로 간주됩니다.
class RoundFloat(float):
def __new__(cls, val):
return float.__new__(cls, round(val, 2))
이것은 클래스 구조 / 계층 때문에 불변으로 간주됩니까?, 의미 float는 클래스의 최상위에 있으며 자체 메서드 호출입니다. 이 유형의 예제와 비슷합니다 (내 책 dict이 변경 가능 하다고 말하더라도 ).
class SortedKeyDict(dict):
def __new__(cls, val):
return dict.__new__(cls, val.clear())
변경 가능한 것은 클래스 내부에 메소드가 있지만이 유형의 예제는 다음과 같습니다.
class SortedKeyDict_a(dict):
def example(self):
return self.keys()
또한 마지막 class(SortedKeyDict_a)유형에 대해이 유형의 세트를 전달하면 :
d = (('zheng-cai', 67), ('hui-jun', 68),('xin-yi', 2))
example메소드 를 호출하지 않고 사전을 리턴합니다. SortedKeyDict와 __new__오류로 플래그를. RoundFloat클래스에 정수를 전달하려고 시도했지만 __new__오류가 표시되지 않았습니다.
답변
뭐? 플로트는 불변입니까? 하지만 난 못해
x = 5.0
x += 7.0
print x # 12.0
“mut”x 아닌가?
글쎄, 문자열이 변경 불가능하다는 데 동의합니까? 그러나 같은 일을 할 수 있습니다.
s = 'foo'
s += 'bar'
print s # foobar
변수의 값은 변하지 만 변수가 참조하는 것을 변경하면 변합니다. 변경 가능한 유형은 이러한 방식으로 변경 될 수 있으며 “제자리에서”변경 될 수도 있습니다.
차이점이 있습니다.
x = something # immutable type
print x
func(x)
print x # prints the same thing
x = something # mutable type
print x
func(x)
print x # might print something different
x = something # immutable type
y = x
print x
# some statement that operates on y
print x # prints the same thing
x = something # mutable type
y = x
print x
# some statement that operates on y
print x # might print something different
구체적인 예
x = 'foo'
y = x
print x # foo
y += 'bar'
print x # foo
x = [1, 2, 3]
y = x
print x # [1, 2, 3]
y += [3, 2, 1]
print x # [1, 2, 3, 3, 2, 1]
def func(val):
val += 'bar'
x = 'foo'
print x # foo
func(x)
print x # foo
def func(val):
val += [3, 2, 1]
x = [1, 2, 3]
print x # [1, 2, 3]
func(x)
print x # [1, 2, 3, 3, 2, 1]
답변
파이썬은 모든 데이터를 객체로 나타냅니다. 목록 및 사전과 같은 일부 개체는 변경 가능하므로 ID를 변경하지 않고 내용을 변경할 수 있습니다. 정수, 부동 수, 문자열 및 튜플과 같은 다른 객체는 변경할 수없는 객체입니다. 이해하기 쉬운 방법은 객체 ID를 살펴 보는 것입니다.
아래에는 불변의 문자열이 있습니다. 내용을 변경할 수 없습니다. 그것은을 올릴 것이다 TypeError당신이 그것을 변경하려고합니다. 또한 새 컨텐츠를 할당하면 컨텐츠를 수정하는 대신 새 오브젝트가 작성됩니다.
>>> s = "abc"
>>>id(s)
4702124
>>> s[0]
'a'
>>> s[0] = "o"
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'str' object does not support item assignment
>>> s = "xyz"
>>>id(s)
4800100
>>> s += "uvw"
>>>id(s)
4800500
목록으로 그렇게 할 수 있으며 객체의 정체성을 바꾸지 않습니다.
>>> i = [1,2,3]
>>>id(i)
2146718700
>>> i[0]
1
>>> i[0] = 7
>>> id(i)
2146718700
Python의 데이터 모델에 대한 자세한 내용을 보려면 Python 언어 참조를 살펴보십시오.
답변
일반적인 불변 유형 :
- 번호 :
int(),float(),complex() - 불변 서열 :
str(),tuple(),frozenset(),bytes()
일반적인 가변 유형 (거의 모든 것) :
- 가변 시퀀스 :
list(),bytearray() - 세트 유형 :
set() - 매핑 유형 :
dict() - 클래스, 클래스 인스턴스
- 기타
유형이 변경 가능한지 여부를 신속하게 테스트하는 한 가지 방법은 id() 내장 기능 하는 것입니다.
정수를 사용하는 예,
>>> i = 1
>>> id(i)
***704
>>> i += 1
>>> i
2
>>> id(i)
***736 (different from ***704)
목록을 사용하여
>>> a = [1]
>>> id(a)
***416
>>> a.append(2)
>>> a
[1, 2]
>>> id(a)
***416 (same with the above id)
답변
우선, 클래스에 메소드가 있는지 또는 클래스 구조가 변경되는지 여부는 변경 가능성과 관련이 없습니다.
ints 및 floats는 변경할 수 없습니다 . 만약 내가한다면
a = 1
a += 5
이름 a이1첫 번째 행의 메모리 어딘가에 . 두 번째 줄에, 그를 조회 1, 추가 5취득, 6다음 점을 a그에서 6메모리에 – 그것은하지 않았다 변경1 A와를 6어떤 식 으로든. 다른 변경 불가능한 유형을 사용하여 다음 예제에 동일한 논리가 적용됩니다 .
b = 'some string'
b += 'some other string'
c = ('some', 'tuple')
c += ('some', 'other', 'tuple')
내용은 변경 가능한 유형, 나는 actallly 일 할 수있는 이 메모리에 저장된 값을 변경을 . 와:
d = [1, 2, 3]
나는의 위치 목록을 만들었습니다 1, 2그리고 3메모리를. 내가한다면
e = d
난 그냥 포인트 e받는 동일한list d 에서 포인트. 그런 다음 할 수 있습니다 :
e += [4, 5]
그리고 지점 e과 d지점이 업데이트되어 목록이 4및5 메모리를.
불변 유형 으로 돌아가서 tuple다음 과 같이하면 :
f = (1, 2, 3)
g = f
g += (4, 5)
그때 f 여전히 원본tuple 만 가리 킵니다 g. 완전히 새로운 것을 가리 켰 습니다.tuple . .
이제, 당신의 예를 들어
class SortedKeyDict(dict):
def __new__(cls, val):
return dict.__new__(cls, val.clear())
당신이 통과하는 곳
d = (('zheng-cai', 67), ('hui-jun', 68),('xin-yi', 2))
(A 인 tuple의 tuples등) val때문에, 오류를 받고있어 tuple의가없는 .clear()방법을 – 당신이 통과해야 할 것 dict(d)같은 val일에 대한 당신이 빈 얻을 것이다 경우에, SortedKeyDict결과를.
답변
다른 언어 (루비와 같이 파이썬과 비슷한 언어는 제외)에서 파이썬으로오고 다른 언어로 이해하려고하면 사람들이 혼란스러워하는 부분은 다음과 같습니다.
>>> a = 1
>>> a = 2 # I thought int was immutable, but I just changed it?!
파이썬에서 할당은 파이썬에서 돌연변이가 아닙니다.
C ++ 에서을 쓰면을 a = 2호출 a.operator=(2)하여에 저장된 객체를 변경합니다 a. (그리고 저장된 물건 이 없다면a 오류입니다.)
파이썬에서는 a = 2저장된 모든 것에 아무 것도하지 않습니다 a. 그것은 단지 2지금 a대신에 저장 된다는 것을 의미합니다 . (에 저장된 객체 가 없으면 a괜찮습니다.)
궁극적으로 이것은 더 깊은 구별의 일부입니다.
C ++와 같은 언어의 변수는 메모리의 형식화 된 위치입니다. 경우 a입니다 int, 그 수단은 컴파일러가 해석하도록되어 알고있는 4 바이트 곳입니다 int. 따라서 그렇게하면 a = 24 바이트의 메모리에 저장된 내용을 0, 0, 0, 1에서0, 0, 0, 2 . 다른 곳에서 다른 int 변수가 있으면 자체 4 바이트가 있습니다.
파이썬과 같은 언어의 변수는 생명력이있는 객체의 이름입니다. 숫자에 대한 객체 1와 숫자 에 대한 다른 객체가 2있습니다. 그리고 a로 표현되는 4 바이트의 메모리가 int아니라 1객체 를 가리키는 이름 일뿐 입니다. a = 2숫자 1을 숫자 2로 바꾸는 것은 이치에 맞지 않습니다 (파이썬 프로그래머에게 우주의 기본 작업을 변화 시키기에는 너무 많은 힘을 줄 것입니다). 대신 객체를 a잊어 버리고 1객체를 가리 키십시오 2.
할당이 돌연변이가 아닌 경우에 따라서, 무엇 이다 돌연변이는?
- 같은 돌연변이 문서화하는 방법을 호출
a.append(b). (이러한 메소드는 거의 항상을 반환None합니다.) 불변 유형에는 그러한 메소드가 없으며 일반적으로 변경 가능한 유형이 있습니다. a.spam = b또는 과 같이 객체의 일부에 할당a[0] = b. 불변 유형은 속성 또는 요소에 대한 할당을 허용하지 않으며, 가변 유형은 일반적으로 둘 중 하나를 허용합니다.- 때로는과 같이 확장 된 할당을 사용하는
a += b경우가 종종 있습니다. 가변 유형은 일반적으로 값을 변경합니다. 불변 유형은 절대로하지 않고 대신 사본을 제공합니다 (계산a + b후 결과를에 할당a).
그러나 할당이 돌연변이가 아닌 경우 객체 돌연변이의 일부에 할당하는 방법은 무엇입니까? 그것이 까다로워지는 곳입니다. a[0] = b하지 아니 하는 mutate a[0](다시, C는 달리 ++),하지만 하지 의 mutate를a 간접적으로 제외하고 C ++과 달리 .
이 모든 것은 아마 더 나은 이유가 없습니다 당신이 사용하는 언어의 관점에서 파이썬의 의미를 넣어 시도하고 대신 자신의 조건에 파이썬의 의미를 배울 수 있습니다.
답변
객체가 변경 가능한지 여부는 유형에 따라 다릅니다. 이것은 특정 메소드가 있는지 여부 또는 클래스 계층 구조에 의존하지 않습니다.
사용자 정의 형식 (예 : 클래스)은 일반적으로 변경 가능합니다. 불변 유형의 단순한 서브 클래스와 같은 예외가 있습니다. 다른 불변의 유형에는 몇 가지 기본 유형과 같은 int, float, tuple및str 뿐만 아니라 일부 파이썬 클래스 C로 구현 된,
“Python Language Reference”의 “Data Model”장에 대한 일반적인 설명 :
일부 개체의 값은 변경 될 수 있습니다. 값을 변경할 수있는 객체는 변경 가능하다고합니다. 일단 생성 된 값을 변경할 수없는 객체를 불변이라고합니다.
(변경 가능한 객체에 대한 참조가 포함 된 변경 불가능한 컨테이너 객체의 값은 후자의 값이 변경 될 때 변경 될 수 있지만, 포함 된 객체의 컬렉션을 변경할 수 없기 때문에 컨테이너는 여전히 불변으로 간주됩니다. 따라서 불변성은 엄격하지 않습니다. 변경 불가능한 값을 갖는 것과 동일하게 더 미묘합니다.)
객체의 가변성은 유형에 따라 결정됩니다. 예를 들어 숫자, 문자열 및 튜플은 변경할 수 없지만 사전과 목록은 변경할 수 있습니다.
답변
가변 객체와 불변 객체의 차이점
정의
가변 객체 : 생성 후 변경할 수있는 객체입니다.
불변 객체 : 생성 후 변경할 수없는 객체입니다.
파이썬에서는 불변 객체의 값을 변경하면 새로운 객체가 생성됩니다.
가변 객체
다음은 파이썬에서 변경 가능한 유형의 객체입니다.
listDictionarySetbytearrayuser defined classes
불변 개체
다음은 불변 유형의 Python 객체입니다.
intfloatdecimalcomplexboolstringtuplerangefrozensetbytes
답변되지 않은 질문
질문 : 문자열은 불변 유형입니까?
답 : 예 , 그러나 당신은 이것을 설명 할 수 있습니다 :
증명 1 :
a = "Hello"
a +=" World"
print a
산출
"Hello World"
위 예제에서 문자열은 “Hello”로 생성 된 후 “Hello World”로 변경되었습니다. 이는 문자열이 변경 가능한 유형임을 의미합니다. 그러나 변경 가능한 유형인지 여부를 확인하기 위해 ID를 확인할 때가 아닙니다.
a = "Hello"
identity_a = id(a)
a += " World"
new_identity_a = id(a)
if identity_a != new_identity_a:
print "String is Immutable"
산출
String is Immutable
증명 2 :
a = "Hello World"
a[0] = "M"
산출
TypeError 'str' object does not support item assignment
질문 : Tuple은 불변 타입입니까?
답 : 네 , 그렇습니다 .
증명 1 :
tuple_a = (1,)
tuple_a[0] = (2,)
print a
산출
'tuple' object does not support item assignment
