[python] ‘자기’라는 단어의 목적은 무엇입니까?

self파이썬 에서 단어 의 목적은 무엇입니까 ? 나는 그것이 그 클래스에서 생성 된 특정 객체를 참조한다는 것을 이해하지만, 왜 그것이 모든 함수에 매개 변수로 명시 적으로 추가되어야하는지 알 수 없습니다. 예를 들어, Ruby에서는 다음과 같이 할 수 있습니다.

class myClass
    def myFunc(name)
        @name = name
    end
end

아주 쉽게 이해할 수 있습니다. 그러나 파이썬에서는 self다음 을 포함해야합니다 .

class myClass:
    def myFunc(self, name):
        self.name = name

누구든지 이것을 통해 나에게 이야기 할 수 있습니까? 내가 경험 한 바에 따르면 내가 경험 한 것은 아니다.



답변

self.파이썬이 @구문을 사용하여 인스턴스 속성을 참조 하지 않기 때문에 사용해야하는 이유 입니다. 파이썬은 메소드가 속한 인스턴스가 자동으로 전달 되지만 자동으로 수신 되지 않는 방식으로 메소드를 수행하기로 결정했습니다. 메소드 의 첫 번째 매개 변수는 메소드가 호출되는 인스턴스입니다. 그것은 메소드를 함수와 완전히 동일하게 만들고 실제 이름을 당신이 사용할 수 있도록 남겨 둡니다 ( self관습은 있지만 사람들이 일반적으로 다른 것을 사용할 때 당신을 찌푸리게 할 것입니다). self코드에 특별하지는 않습니다 . .

파이썬은 일반 이름과 속성 (Ruby와 같은 특수 구문, C ++ 및 Java와 같은 선언이 필요하거나 더 다른 것)을 구별하기 위해 다른 것을 할 수 있었지만 그렇지 않았습니다. 파이썬은 모든 것을 명시 적으로 만들고, 무엇이 무엇인지를 분명하게하며, 모든 곳에서 그것을하지는 않지만 인스턴스 속성을 위해 수행합니다. 그렇기 때문에 인스턴스 속성에 할당 할 인스턴스를 할당해야하는 이유가 필요합니다 self..


답변

간단한 벡터 클래스를 보자.

class Vector:
    def __init__(self, x, y):
        self.x = x
        self.y = y

우리는 길이를 계산하는 방법을 원합니다. 클래스 내에서 정의하고 싶다면 어떻게 될까요?

    def length(self):
        return math.sqrt(self.x ** 2 + self.y ** 2)

전역 메소드 / 함수로 정의 할 때 어떤 모습이어야합니까?

def length_global(vector):
    return math.sqrt(vector.x ** 2 + vector.y ** 2)

따라서 전체 구조는 동일하게 유지됩니다. 이것을 어떻게 활용할 수 있습니까? 우리가 수업에 대한 length방법을 쓰지 않았다고 가정하면 다음 Vector과 같이 할 수 있습니다.

Vector.length_new = length_global
v = Vector(3, 4)
print(v.length_new()) # 5.0

의 첫 번째 매개 변수가 있기 때문에 작품 length_global의로 재사용 할 수 self있는 매개 변수 length_new. 명시 적 없이는 불가능합니다 self.


명시 적의 필요성을 이해하는 또 다른 방법은 self파이썬이 구문 설탕을 추가하는 위치를 보는 것입니다. 명심하면 기본적으로

v_instance.length()

내부적으로

Vector.length(v_instance)

어디에 self맞는지 쉽게 알 수 있습니다 . 실제로 파이썬에서 인스턴스 메소드를 작성하지는 않습니다. 작성하는 것은 첫 번째 매개 변수로 인스턴스를 가져와야하는 클래스 메서드입니다. 따라서 인스턴스 매개 변수를 명시 적 어딘가에 배치해야합니다.


답변

다음 과 같이 정의 된 ClassA메소드를 포함하는 클래스가 있다고 가정하십시오 methodA.

def methodA(self, arg1, arg2):
    # do something

그리고 ObjectA이 클래스의 인스턴스입니다.

이제 ObjectA.methodA(arg1, arg2)호출되면 파이썬은 내부적으로 다음과 같이 변환합니다.

ClassA.methodA(ObjectA, arg1, arg2)

self변수 객체 자체를 의미한다.


답변

객체가 인스턴스화되면 객체 자체가 자체 매개 변수로 전달됩니다.

여기에 이미지 설명을 입력하십시오

이로 인해 객체의 데이터가 객체에 바인딩됩니다. 아래는 각 객체의 데이터가 어떻게 보이는지 시각화하는 방법의 예입니다. ‘self’가 어떻게 객체 이름으로 대체되는지 확인하십시오. 아래 예제 다이어그램이 완전히 정확하다고 말하지는 않지만 자아 사용을 시각화하는 목적으로 사용되기를 바랍니다.

여기에 이미지 설명을 입력하십시오

오브젝트는 자체 매개 변수로 전달되므로 오브젝트가 자체 데이터를 보유 할 수 있습니다.

이것이 완전히 정확하지는 않지만 다음과 같이 객체를 인스턴스화하는 프로세스를 생각해보십시오. 객체가 만들어 질 때 클래스는 자체 데이터 및 메소드의 템플리트로 클래스를 사용합니다. 자체 매개 변수에 자체 이름을 전달하지 않으면 클래스의 속성과 메서드는 일반 템플릿으로 유지되며 객체와 관련하여 참조되지 않습니다. 따라서 객체 이름을 self 매개 변수에 전달하면 하나의 클래스에서 100 개의 객체를 인스턴스화하면 모두 자신의 데이터와 메서드를 추적 할 수 있습니다.

아래 그림을 참조하십시오.

여기에 이미지 설명을 입력하십시오


답변

나는이 예를 좋아한다 :

class A:
    foo = []
a, b = A(), A()
a.foo.append(5)
b.foo
ans: [5]

class A:
    def __init__(self):
        self.foo = []
a, b = A(), A()
a.foo.append(5)
b.foo
ans: []


답변

클래스를 사용하지 않는 코드로 시연하겠습니다 .

def state_init(state):
    state['field'] = 'init'

def state_add(state, x):
    state['field'] += x

def state_mult(state, x):
    state['field'] *= x

def state_getField(state):
    return state['field']

myself = {}
state_init(myself)
state_add(myself, 'added')
state_mult(myself, 2)

print( state_getField(myself) )
#--> 'initaddedinitadded'

클래스는이 “상태”항목을 항상 전달하지 않도록하는 방법 일뿐입니다 (초기화, 클래스 구성, 거의 필요하지 않은 메타 클래스 및 연산자 재정의를위한 사용자 정의 메소드 지원과 같은 다른 좋은 것).

이제 내장 된 파이썬 클래스 기계를 사용하여 위 코드를 시연 해 보자. 기본적으로 동일한 것을 보여 주겠다.

class State(object):
    def __init__(self):
        self.field = 'init'
    def add(self, x):
        self.field += x
    def mult(self, x):
        self.field *= x

s = State()
s.add('added')    # self is implicitly passed in
s.mult(2)         # self is implicitly passed in
print( s.field )

[중복 된 질문에서 답변을 마이그레이션했습니다]


답변

다음 발췌는 self에 대한 Python 문서 에서 발췌 한 것입니다 .

Modula-3에서와 같이, 메소드에서 객체의 멤버를 참조하기위한 [Python에서는] 속기가 없습니다. 메소드 함수는 객체를 나타내는 명시적인 첫 번째 인수로 선언되며, 이는 호출에 의해 암시 적으로 제공됩니다.

종종 메소드의 첫 번째 인수를 self라고합니다. 이것은 규칙에 지나지 않습니다. self라는 이름은 파이썬에 특별한 의미가 없습니다. 그러나 규칙을 따르지 않으면 코드를 다른 Python 프로그래머가 읽을 수 없을 수 있으며 이러한 규칙에 의존하는 클래스 브라우저 프로그램을 작성할 수도 있습니다.

자세한 정보 는 클래스Python 문서 학습서를 참조하십시오 .