Python Tutorial

[ Python Tutorial ] 클래스

공대아빠 JSLEE 2022. 12. 26. 10:01
클래스
  • 클래스 개념
  • 생성자, 소멸자
  • self
  • 네임스페이스 (namespace)
  • 클래스에서의 getter / setter 사용
  • 클래스 변수(class variable) vs 인스턴스 변수(instance variable)
  • 인스턴스 메서드 & 클래스 메서드 (class method) & 정적 (static) 메서드
  • 상속 / super

 

 

클래스
  • 빵을 만드는 틀" 개념
  • 객체(object) : 클래스를 통해 만들어진 빵의 개념
  • 객체와 인스턴스 차이
    • 같은 것이나 누구 관점에서 부르르냐의 창
    • object = Test()  
      • object 는 객체라고 부르며, Test 는 클래스라고 부름
      • Test 클래스 관점에서 부르면 object는 Test의 인스턴스라고 함
    • 인스턴스 : 클래스를 실체화한것. 즉, 클래스로 객체화 한것을 인스턴스라고함
  • 메소드 : 클래스 내 함수
  • 클래스 생성 시, 대문자로 작성
# class 생성

class Person:
	pass
    
p = Person()	# 객체 생성
  • 객체를 생성하면 아래 그림과 같이 클래스와 객체가 각자 고유의 메모리 공간을 가짐

  • p.data = 3 입력 시, 아래와 같이 p 객체 공간에 {"data":3} 을 딕셔너리 형태로 저장함. 

 

생성자 (constructor), 소멸자
  • 생성자 : 클랙스 객체 생성 시 자동으로 실행되는 것. 초기값 설정 시 사용
  • 소멸자 : 클래스 인스턴스가 소멸될 때 자동으로 호출되는 함수. 일반적으로 잘 사용하지 않음
  • self   :  클래스 인스턴스, 아래의 경우, self 는 test 가 됨
# 생성자, 소멸자

class Test:
	def __init__(self, name, age):	# 생성자
    	self.name = name
        self.age = age
    
    def __del__(self):
    	print('소멸자')
    

# 객체 생성
test = Test('JS', 23)

# 객체 접근
print(test.name)
print(test.age)

 

 

self
  • 클래스 내의 인스터스를 의미함
class Foo:
    def func1():
        print(f'func1')

    def func2(self):
        print(id(self))
        print(f'func2')
        

f1 = Foo()
# f1.func1()  # error
f1.func2()

print(id(f1))   # f1 instance 주소와 self의 주소가 같음

 

 

네임스페이스
  • 변수가 객체를 바인딩할 때 그 둘 사이의 관계를 저장하는  공간을 의미함
  • 파이썬 클래스는 새로운 타입(객체)을 정의하기 위해 사용되며, 모듈과 마찬가지로 하나의 네임스페이스를 가짐

 

클래스에서의 getter / setter 사용
  • 클래스의 데이터를 직접 변경하는 것은 좋지 않음. 즉, 간접적으로 조작하는 것이 좋음 (get, set 사용)
  • 파이썬에는 private, public 개념이 없음
  • 아래 코드에서 그냥 get, set 함수를 사용하면 여전히 사용이 가능함
  • @property , @age.setter 데코레이터를 사용하여 코드를 작성하는 것이 좋음
  • 앞 언더바 2개 사용 
    • 외부에서 클래스 속성값에 접근하지 못하도록 할때
    • 오바라이딩 방지용
class Test:
	def __init__(self, name, age):
    	self.__name = name
        self.__age = age
 	
    def get(self):
        return self.__name, self.__age
    
    def set(self, name, age):
        self.__name = name
        self.__age = age
        
    @property
    def age(self):
        return self.__age


    @age.setter
    def age(self, age):
        self.__age = age
    
    
    
# 객체 생성
test = Test('JS', 11)

# 직접 변경
test.name = 'SJ'
test.age = '22'
 
# get
name, age = test.get()
print(name, age)

# set
test.set('JS', 33)
name, age = test.get()
print(name, age)


# property
print(test.age)	# getter
test.age = 20	# setter

test.name = 'DH'	#  변경 안됨

 

 

클래스 변수(class variable) vs 인스턴스 변수(instance variable)
  • 클래스 변수
    • 여러 인스턴스 간에 서로 공유해야하는 값은 클래스 변수를 사용
  • 인스턴스 변수
    • self 가 붙어있는 변수
class Account:
    num_account = 0		# class variable
    def __init__(self, name):
    	self.name = name	# intance variable
        Account.num_account += 1
        

kim = Account('kim')
lee = Account('lee')

 

인스턴스 메서드 & 클래스 메서드 (class method) & 정적 (static) 메서드
  • 인스턴스 메서드
    • 클래스에 아무 데코레이터 없이 선언된 메서드
    • 첫번째 매개 변수로 클래스의 인스턴스가 넘어옴 (= self)
  • 클래스 메서드
    • @classmethod 데코레이터를 사용하여 선언
    • 첫번째 매개 변수로 클래스 인스턴스가 아닌 클래스 자체가 넘어옴 (= cls)
    • cls 를 사용해 클래스 속성에 접근하거나 클래스 메서드를 호출 할 수 있음
    • 인스턴스 메서드와 달리 다른 인스턴스 속성에 접근하거나 다른 인스턴스 메서드를 호출하는 것은 불가능함.
    • 팩토리 메서드를 작성할 때 유용함
  • 정적 메서드
    • @staticmethod 데코레이터 사용하여 선언
    • 첫번째 매개 변수가 할당 되지 않음
    • 클래스의 일부로 선언할 필요 없지만 비슷한 메서드를 하나의 클래스에 두고 싶을때 사용
    • 정적 메서드 내에서는 인스턴스, 클래스 속성에 접근하거나 호출하는 것이 불가능
class Test:
    object_count = 0    # class variable
    
    def __init__(self, age):
        self.age = age
        
        Test.object_count += 1

    # instance method
    def add(self, age):
        return self.age + age
    
    # class method
    @classmethod
    def count(cls):
        return cls.object_count

    # static method
    @staticmethod   
    def static(name):
        print(name)


# instance method
test = Test(10)
print(test.age)

# class method
t1 = Test(10)
print(t1.count())
t2 = Test(20)
print(t2.count())

# static method
t2.static('static')

 

 

상속 / super
  • 부모 클래스(parent class, super class), 자식 클래스(child class, sub class) 
  • 메소드 오버라이딩 (method overriding)
    • 부모 클래스의 메소드를 자식 클래스에서 재정의 하는것
  • 파이썬은 다중상속이 가능함(c++가능, C#, Java 불가능)
# parent class
class Parent:
    def __init__(self, name, age):
        self.name = name
        self.age = age
    
    def showParent(self):
        print(self.name, self.age)

# child class
class Child(Parent):    # 상속
    def __init__(self, name, age):
        super().__init__(name, age)     # parent class init() 상속
        
    
    def showChild(self):
        super().showParent()    # method oeverriding
        print('child show')


p = Parent('JS', 10)
p.showParent()

c = Child('TT', 20)
c.showParent()  # 부모 클래스 함수도 사용 가능
c.showChild()

 

 

추상 클래스 (abstract class)
  • 추상 클래스는 메서드의 이름만 존재하는(메서드 구현 없이) 클래스
  • 부모 클래스에 메서드만을 정의하고, 이를 상속 바은 클래스가 해당 메서드를 구현하도록 강제하기 위해서 사용함
# parent class
class Car:
	@abstracmethod
    def drive(self):
    	pass
        
        
class K5(Car):
	def drive(self):
    	print('k5 drive')


car_k5 = K5()