python class2 상속

kangjuju·2023년 4월 13일
0

python

목록 보기
3/4

class Dog(Animal):

  • 자식클래스를 선언할때 소괄호로 부모클래스를 포함시킨다.
    그러면 자식클래스에서는 부모클래스의 속성과 메소드는 기재하지 않아도 포함이 된다.
class Animal: 
    def move(self):
        print('움직이는 생물')
        
class Dog(Animal):  #상속의 기본형
    def myNameIs(self):
        print('댕댕이')

dog1 = Dog() 
dog1.move() #부모 메소드
dog1.myNameIs() #본인의 메소드

먼저 자식Dog의 생성자를 찾고, Dog의 생성자가 없다면 부모의 생성자를 실행한다.
자식의 생성자를 실행할 경우 부모의 생성자는 호출되지 않는 점이 자바와의 차이점이다.

자식클래스에서 같은이름의 move 메소드를 구현한다면 재정의도 가능하다.
당연하듯이 자식에서 재정의 된 메소드가 우선순위가 높다.

super

class Person:
    say = '사람입니다.'
    nai = 20
    def __init__(self,nai):
        print('person생성자')
        self.nai = nai  
    def printInfo(self):
        print('나이:{},이야기:{}'.format(self.nai,self.say))  
    def Hello(self):
        print('안녕')
        
class Employee(Person):
    say = '일하는 동물' #재정의된 해당 멤버변수를 우선적으로 사용한다.
    subject = '근로자'
    def __init__(self, nai):
        print('employee생성자')
    
#   def printInfo(self): 
#      print('employee의 printInfo')
    def empPrintInfo(self):
        self.printInfo() #imployee의 메소드를 찾고, 없다면 부모를 이용한다.
    
emp = Employee(11)
#emp.printInfo() 
emp.empPrintInfo()

위 클래스에서 print(self.printInfo,super().say,subject) 구문을 사용할때, 이 안에 3개의 각 우선순위를 정리해두고 넘어가는것이 좋다.

  • self.~ : 본인의 클래스에서 멤버를 먼저 찾고, 없다면 부모에서 찾는다.

  • super().~ : 부모클래스에서 멤버를 찾는다.

  • 없음 : 해당 메소드의 지역변수를 먼저 찾고, 없다면 모듈, 전역변수를 찾는다.

메소드를 같은 이름으로 사용하면서 재정의 또한 가능하다.
단, 자식메소드를 사용 후 부모의 메소드를 찾지않는다는 특징을 기억하자.


self의 특성상 자식의 멤버를 먼저 확인하고, 없다면 부모의 멤버를 호출하는 법칙을 항상 따른다.
여기서 super().printInfo() 또는 super().say 와 같이 부모의 멤버를 명시한다면 처음부터 부모멤버를 사용한다.

#명시적으로 부르지 않는 이상 Employee의 멤버변수인 say를 사용하게된다.
# super로 부모의 멤버에 접근해보자.

class Worker(Person):
    def __init__(self, nai):
        #부모 클래스의 생성자를 명시적 호출 - Bound Method call
        super().__init__(nai)
        
    def workPrintInfo(self):
        self.printInfo()
        
work = Worker('33')
print(work.say, ' ' ,work.nai)
work.workPrintInfo()     

Person의 자식. Worker의 인스턴스 work를 생성하게 되면서 시작된다.

Worker class에서 work 인스턴스의 주소가 self로 타고 넘어다니고,
각 변수의 우선순위를 찾으며 출력될 멤버들이 결정된다.

위 코드와 같은 경우는 work생성시 '33'으로 생성자에게 nai를 지정하였고,
super().__init__(nai) 에 의해 work객체 부모의 nai변수에게 전달되었다.(덮어씌워짐)

그 후 출력메소드로 결과를 확인해기 위해 self.printInfo() 를 실행했는데, 여기서 self의 특성이 또다시 등장한다.
Worker의 printinfo()를 먼저 찾고, 없다면 부모의 메소드(printinfo())를 호출한다.
결과 : 나이:33,이야기:사람입니다.

다중상속

위의 Worker클래스의 자식 Programmer를 만들어보자. (다중상속)

class Programmer(Worker):
    def __init__(self, nai):
        print('programmer 생성자')
        super().__init__(nai)
        #Worker.__init__(self,nai) #UnBound method call

    def workPrintInfo(self):
        print('Programmer 에서의 WorkPrintInfo override 재정의')
        self.printInfo()

pr = Programmer('28')
print(pr.say,' ',pr.nai)

Person의 자식 Worker.
Worker의 자식인 Programmer 클래스이다. 자식의 자식클래스의 멤버 변수를 사용하려고 한
모든 멤버를 사용할때 생각해야하는 점은 본인의 멤버변수에 없다면 순차적으로 그 위, 또 없으면 그 위인 Person 부모 메소드의 멤버를 사용한다.


참고

__bases__

현재클래스의 부모확인. 다중상속이 가능하기 때문에 복수가 될 수 있는점에 의해 튜플로 반환한다.

print(Programmer.__bases__)  #(<class '__main__.Worker'>,)
print(Person.__bases__) #(<class 'object'>,)

private멤버

자신의 클래스 이외에서는 호출할 수 없다.
__ 언더바 2개를 선행해서 작성하면 된다. 사용빈도는 낮음

class Person:
    __kor = 'good'

@staticmethod

인스턴스없이 클래스만으로 부를 수 있다.
데코레이터를 사용하여 선언한다.

    @staticmethod
    def sbs(tel):
        print('sbs static method의 tel',tel)
        
Person.sbs('222-2222') 

0개의 댓글