이 글은 도서 '점프 투 파이썬' 을 토대로 개인적으로 정리한 내용입니다.

class

  • class란 똑같은 무엇인가를 계속해서 만들어 낼 수있는 설계 도면이다.
  • 객체(object)란 클래스로 만든 피조물을 뜻한다.
  • 클래스로 만든 객체에는 고유한 성격을 가진다.
  • 객체들 간에 서로 영향을 주지 않는다.
  • 파이썬에서 class를 사용하는 것이 필수요소는 아니다. 하지만 적재적소에 사용한다면 유용한 기능이 될 수 있다.

더하기 기능이 있는 클래스를 한번 만들어보자.

입력

class Calculator:
    def __ini__(self):
         self.result = 0
    def add(self, num):
    	self.result += num
        return self.result
cal1 = Calculrator()
cal2 = Calculrator()
print(cal1.(3))
print(cal1.(4))
print(cal2.(3))
print(cal2.(7))

출력

3
7
3
10

cal1 = Calculrator()
cal2 = Calculrator()
Calculrator 클래스를 사용하는 객체 cal1, cal2를 생성하였다. 객체는 서로 독립된 값을 가지므로 서로 영향을 받거나 주지 않는다.

만약 Calculrator클래스에 빼기 기능을 추가하고 싶다면 다음과 같은 함수를 추가하면 된다.

def sub(self, num):
    self.result -= num
    return selr.result

여러 함수를 추가 원하는 기능이 있는 class를 만들 수 있다.

클래스와 객체의 관계를 간단히 살펴보자.

class Cookie:
    pass
  • 아무 기능이 없는 껍질뿐인 class를 생성할 수 있다.. 아무 기능이 없는 class도 객체를 생성할 수 있다.
  • 1개의 클래스는 무수히 많은 객체를 만들어 낼 수 있다.

아래 클래스로 객체를 만드는 방법을 살펴보자.

a = Cookie()
b = Cookie()
...

Cookie()의 결과값을 돌려받는 a, b가 객체이다.

1. 사칙연산 class 만들기

- 사칙연산에 사용될 숫자 2개 입력 함수 만들기

class FourCal:
    def setdata(self, first, second):
        self.first = first
        self.second = second
  • 클래스 안에 구현된 함수를 다른말로 메서드(Method)라 부른다.
  • setdata에 메서드는 매개변수로 self, first, second3개의 입력값을 받는다.

일반 함수와 달리 메서드의 첫 번째 변수 self는 특별한 의미를 가진다. 아래의 예시에서 한번 살펴보자.

a = FourCal()
a.setdata(4, 2)

setdata메서드에는 self,first,second 총 3개의 매개변수가 필요한데 실제로는 a.setdata(4,2)처럼 2개 값만 전달했다. 그 이유는 a.setdata(4,2)처럼 호출하면 setdata 메서드의 첫 번째 매개변수 self에는 setdata메서드를 호출한 객체 a가 자동으로 전달되기 때문이다.

  • a => self
  • 4 => first
  • 2 => second

객체를 호출할 때 입력한 값이 메서드에 어떻게 대응하여 전달되는지 볼 수 있다.

  • 파이썬 메서드의 첫 번째 매개변수 이름을 관례적으로 self로 사용한다.
  • 객체를 호출할 때 호출한 객체 자신이 전달되기 때문에 self를 사용한 것이다.
  • self말고 다른 이름을 사용해도 상관은 없다.

- 더하기 기능 만들기

class FourCal:
    def setdata(self, first, second):
        self.first = first
        self.second = second
   def add(self):
       result = self.first + self.second
       reture result

새롭게 add 메서드를 추가하였다. 클래스를 사용해보자.

  • setdata 메서드에 객체변수에 값 저장
    a = FourCal()
    a.setdata(4,2)
  • add 메서드 호출
    print(a.add())
  • 출력값
    6

위 내용을 자세히 살펴보자.

  • result = self.first + self.second
    add 메서드의 매개변수는 self값이고 반환 값은 result이다.
  • result = a.first + b.second
    a.add()와 같이 a객체에 의해 add 메서드가 수행되면 add메서드의 self에는 객체 a가 자동으로 입력된다.
  • result = 4 + 2
    a.add()메서드 호출 전에 a.setdata(4,2)가 먼저 호출되어 a.first = 4, a.second = 2 라고 이미 설정되어 있으므로 다음과 같이 해석한다.
  • print(a.add()) -> 6
    a.add()를 호출하면 6을 돌려준다.

더하기 기능과 같은 방법으로 빼기, 곱하기, 나누기 기능을 만들어보자

- 빼기, 곱하기, 나누기 기능 만들기

class FourCal:
    def setdata(self, first, second):
        self.first = first
        self.second = second
    def add(self):
        result = self.first + self.second
        return result
    def sub(self):
        result = self.first - self.second
        return result
    def mul(self):
        result = self.first * self.second
        return result
    def div(self):
        result = self.first / self.second
        return result

2. 생성자(Constructor)

입력

a = FourCal()
a.add()

출력

Traceback (most recent call last):
  File #### ,line # ,in <module>
  File ####, line # ,in add
AttributeError: 'FourCal' object has no attribute 'first'

FourCal클래스의 인스턴스 a에 setdata메서드를 수행하지 않고 add 메서드를 수행하면 AttributeError: 'FourCal' object has no attribute 'first'오류가 발생한다. setdata메서드를 수행해야 객체 a의 객체변수 first와 second가 생성되기 때문이다.

이렇게 객체의 초기값을 설정할 필요가 있을 때는 setdata와 같은 메서드를 호출하여 초기값을 설정하기보다는 생성자를 구현하는 것이 안전한 방법이다. 생성자(Constructor)란 객체가 생성될 때 자동으로 호출되는 메서드를 의미한다.

파이썬 메서드 이름으로 __init__ 를 사용하면 이 메서드는 생성자가 된다.
다음 예시를 통해 생성자를 추가해보자.

class FourCal:
    def __init__(self, first, second):
        self.first = first
        self.second = second
    def setdata(self, first, second):
        self.first = first
        self.second = second
    def add(self):
        result = self.first + self.second
        return result
    def sub(self):
        result = self.first - self.second
        return result
    def mul(self):
        result = self.first * self.second
        return result
    def div(self):
        result = self.first / self.second
        return result

__init__메서드는 setdata와 이름만 다르고 모든게 동일하다. 단 메서드 이름을 __init__으로 했기 때문에 생성자로 인식되어 객체가 생성되는 시점에 자동으로 호출되는 차이점이 있다.

__init__메서드를 생성한 뒤 a = FourCal() 객체를 생성하면 TypeError: __init__() missing 2 required positional arguments: 'first' and 'second' 에러가 발생한다.
그 이유는 생성자의 매개변수 first, second에 해당하는 값이 전달되지 않았기 때문이다. 오류를 해결하기 위해서는 a = FourCal(4, 2) 처럼 매개변수 값을 전달하여야한다.

__init__메서드의 매개변수에 대입된 값을 알아보자.

  • self = 생성되는 객체
  • a = 4
  • b = 2

생성자가 있는 경우와 없는 경우를 예시를 통해 살펴보자.

- 생성자가 있는 경우

입력

class FourCal:
    def __init__(self, first second):
        self.first = first
        self.second = second
    def setdata(self, first, second):
        self.first = first
        self.second = second
    def add(self):
        result = self.first + self.second
        return result
a = FourCal(4, 2)
print(a.add())

출력

6

- 생성자가 없는 경우

입력

class FourCal:
    def setdata(self, first, second):
        self.first = first
        self.second = second
    def add(self):
        result = self.first + self.second
        return result
a = FourCal()
a.setdata(4, 2)
print(a.add())

출력

6

3. 상속

상속(Inheritance)이란?

어떤 클래스를 만들 때 다른 클래스의 기능을 물려받을 수 있게 만드는 것이다.

사칙연산 클래스에 a의 b제곱을 구할 수 있는 기능을 추가하는 예시를 살펴보자.

class MoreFourCal(FourCal):
    pass
class 클래스 이름(상속할 클래스 이름)

MoreFourCal클래스는 FourCal클래스를 상속했으므로 FourCal클래스의 모든 기능을 사용할 수 있다.

a의b제곱 기능을 추가하여보자.

class MoreFourCal(FourCal):
    def pow(self):
        result = self.first ** self.second
        return result
a = MoreFourCal(4, 2)
print(a.pow())

출력

16

상속은 MoreFourCal클래스처럼 기존 클래스(FourCal)는 그대로 놔둔 채 클래스의 기능을 확장시킬 때 주로 사용한다.

-메서드 오버라이딩

입력

a = FourCal(4, 0)
a.div()

출력

ZeroDivisionError: division by zero

div 메서드에서 4를 0으로 나눌려고 하면 ZeroDivisionError에러가 발생한다.
만약 0으로 나눌 때 오류가 아닌 0 으로 나타내고 싶으면 어떻게 해야할까?

FourCal클래스를 상속하는 SafeFourCal 클래스를 만들어 보자.

class SafeFourCal(FourCal)
    def div(self):
        if self.second == 0:
            reture 0
        else:
            return self.first / self.second

SafeFourCalFourCal 에 있는 div메서드를 다시 작성하였다.
부모 클래스에 있는 메서드를 동일한 이름으로 다시 만드는 것을 메서드 오버라이딩(overriding:덮어쓰기) 라고 한다. 부모 클래스의 메서드 대신 오버라이딩한 메서드가 호출된다.

0 이 잘 출력되는시 예시를 통해 확인해보자.

입력

a = SafeFourCal(4, 0)
print(a.div())

출력

0

4. 클래스 변수

  • 객체변수는 다른 객체들에 영향을 받지 않고 독립적으로 그 값을 유지한다.

예시를 통해 클래스 변수를 알아보자.

입력

class Family:
    lastname = "김"
print(Family.lastname)

출력

Family라는 클래스를 만들고 그 안에 lastname이라는 변수를 생성하였다.
클래스 안에 생성한 변수라 하여 클래스 변수이다.

객체를 통해서도 클래스 변수를 사용할 수 있다.

입력

a = Family()
b = Family()
print(a.lastname)
print(b.lastname)

출력

김
김

만약 클래스의 변수를 "박"이라는 문자열로 변경한다면 어떻게 될까?

입력

Family.lastname = "박"
print(a.lastname)
print(b.lastname)

출력

박
박

클래스 변수 값을 변경했더니 클래스로 만든 객체의 lastname값도 모두 변경된다는 것을 확인할 수 있다. 즉 클래스 변수는 클래스로 만든 모든 객체에 공유된다는 특징이 있다.

0개의 댓글

Powered by GraphCDN, the GraphQL CDN