TIL_26 : 객체 지향 프로그래밍
🙄 객체 지향 프로그래밍
➡ 객체란?
- 속성과 행동으로 이루어진 존재
ex) instagram 유저 객체
- 속성 : 이메일 주소, 비밀번호, 친구목록 ...
- 행동 : 좋아요 누르기, 친구 추가하기 ...
현실에 존재하든, 가상으로 존재하든 속성과 행동을 떠올릴 수 있다면 모두 객체
➡ 객체 지향 프로그래밍이란?
- 프로그램을 여러 개의 독립된 객체들과 그 객체들 간의 상호작용으로 파악하는 프로그래밍 접근법
- 프로그램을 객체들과 객체들 간의 소통으로 바라보는 것
👉 객체 지향 프로그래밍으로 프로그램을 만들려면
- 프로그램에 어떤 객체들이 필요할지 정한다
- 객체들의 속성과 행동을 정한다
- 객체들이 서로 어떻게 소통할지 정한다
🙄 객체를 만드는 법
➡ 클래스와 인스턴스
- 객체의 틀을 클래스라고 하고 틀로 만든 결과물을 객체(인스턴스)라고 함
클래스로 객체를 만든다 = 클래스로 인스턴스를 만든다
인스턴스, 객체가 굳이 비교하면 다른거라더라
class User: # 클래스 이름 첫글자는 무조건 대문자
pass # 속성과 행동 입력, 아예 비워 두면 Error
user1 = User() # user1 인스턴스
user2 = User() # user2 인스턴스
user3 = User() # user3 인스턴스
user1, user2, user3는 같은 클래스로 만들었어도 서로 다른 인스턴스
➡ 인스턴스 변수
- 인스턴스 변수 정의하기
:인스턴스 이름.속성이름(인스턴스 변수) = "속성에 넣을 값"
class User:
pass
user1 = User()
user2 = User()
user3 = User()
user1.name = "구자현"
user1.email = "[email protected]"
user1.password = "12345"
user2.name = "민정호"
user2.email = "[email protected]"
user2.password = "24680"
user3.name = "박준규"
user3.email = "[email protected]"
user3.password = "13579"
print(user1.password)
print(user2.email)
print(user3.name)
# 1235
# [email protected]
# 박준규
- 같은 속성이름을 갖고 있더라도 다른 값을 갖고 있다.
- 속성을 공유하는 것이 아닌 각자 개인적으로 소유
- 인스턴스가 개인적으로 갖고 있는 변수를 인스턴스 변수 라고한다
- name, email, password는 모두 인스턴스 변수
➡ 인스턴스 메소드
- 객체의 속성은 인스턴스 변수로 나타낸다
- 객체의 행동은 함수로 나타낸다
행동을 나타내는 함수를 메소드라고 함
👉 메소드의 3가지 종류
1. 인스턴스 메소드 : 인스턴스 변수를 사용하거나, 인스턴스 변수에 값을 설정하는 메소드
2. 클래스 메소드
3. 정적 메소드
class User:
def say_hello(some_user):
# 인사 메세지 출력 메소드
print("안녕하세요! 저는 {}입니다!".format(some_user.name))
user1 = User()
user2 = User()
user3 = User()
user1.name = "구자현"
user1.email = "[email protected]"
user1.password = "12345"
user2.name = "민정호"
user2.email = "[email protected]"
user2.password = "24680"
user3.name = "박준규"
user3.email = "[email protected]"
user3.password = "13579"
User.say_hello(user1)
User.say_hello(user2)
User.say_hello(user3)
# 안녕하세요! 저는 구자현입니다!
# 안녕하세요! 저는 민정호입니다!
# 안녕하세요! 저는 박준규입니다!
name이라는 인스턴스 변수 사용 ➡ 함수
say_hello
는 인스턴스 메소드
👉 인스턴스 메소드의 특별한 규칙_1
- 인스턴스의 메소드를 호출하면 파라미터로 인스턴스를 자동으로 넘겨준다
class User:
def say_hello(some_user):
# 인사 메세지 출력 메소드
print("안녕하세요! 저는 {}입니다!".format(some_user.name))
def login(some_user, my_email, my_password):
# 로그인 메소드
if (some_user.email == my_email and some_user.password == my_password):
print("로그인 성공, 환영합니다")
else:
print("로그인 실패, 없는 아이디이거나 잘못된 비밀번호입니다.")
user1 = User()
user2 = User()
user3 = User()
user1.name = "구자현"
user1.email = "[email protected]"
user1.password = "12345"
User.say_hello(user1) # 클래스에서 메소드를 호출
user1.say_hello() # 인스턴스의 메소드 호출
user1.login("[email protected]", "12345")
# 안녕하세요! 저는 구자현입니다!
# 안녕하세요! 저는 구자현입니다!
# 로그인 성공, 환영합니다
👉 규칙_2 : self 사용
class User:
def say_hello(self):
# 인사 메세지 출력 메소드
print("안녕하세요! 저는 {}입니다!".format(self.name))
def login(self, my_email, my_password):
# 로그인 메소드
if (self.email == my_email and self.password == my_password):
print("로그인 성공, 환영합니다")
else:
print("로그인 실패, 없는 아이디이거나 잘못된 비밀번호입니다.")
user1 = User()
user2 = User()
user3 = User()
user1.name = "구자현"
user1.email = "[email protected]"
user1.password = "12345"
User.say_hello(user1)
user1.say_hello()
user1.login("[email protected]", "12345")
# 안녕하세요! 저는 구자현입니다!
# 안녕하세요! 저는 구자현입니다!
# 로그인 성공, 환영합니다
- 인스턴스 메소드를 정의할 때, 항상 첫 파라미터는 인스턴스를 받기 위한 파라미터를 써줘야함
- python 세계에서는 self를 쓰기로 약속
첫 번째 파라미터의 이름은 꼭❗ self로 쓰기
➡ 인스턴스 변수와 같은 이름의 파라미터
class User:
def check_name(self, name):
# 파라미터로 받는 name이 유저의 이름과 같은지 불린으로 리턴하는 메소드
return self.name == name
user2 = User()
user2.name = "민정호"
user2.email = "[email protected]"
user2.password = "24680"
print(user2.check_name("민정호"))
print(user2.check_name("박준규"))
# True
# False
- 인스턴스의 변수와 파라미터의 이름이 둘다 name으로 동일
아무런 문제 없다 !!
➡ initialize 메소드
- 아래와 같이 메소드를 작성하면 인스턴스 변수를 한번에 설정할 수 있다
class User:
def initialize(self, name, email, password):
self.name = name
self.email = email
self.password = password
user1 = User()
user1.initialize("Young", "[email protected]", "123456")
user2 = User()
user2.initialize("Yoonsoo", "[email protected]", "abcdef")
user3 = User()
User.initialize(user3, "Taeho", "[email protected]", "123abc")
user4 = User()
User.initialize(user4, "Lisa", "[email protected]", "abc123")
print(user1.name, user1.email, user1.password)
print(user2.name, user2.email, user2.password)
print(user3.name, user3.email, user3.password)
print(user4.name, user4.email, user4.password)
# Young [email protected] 123456
# Yoonsoo [email protected] abcdef
# Taeho [email protected] 123abc
# Lisa [email protected] abc123
➡ __init__ 메소드
-
__init__ : 인스턴스가 생성될 때 자동으로 호출되는 특수 메소드
-
인스턴스 생성과 초기값 설정 동시에 가능
-
그래서 보통 클래스에는 __init__ 메소드가 항상 존재
특수 메소드 : 특정 상황에서 자동으로 호출되는 메소드
class User:
def __init__(self, name, email, password):
self.name = name
self.email = email
self.password = password
user1 = User("Young", "[email protected]", "123456")
user2 = User("Yoonsoo", "[email protected]", "abcdef")
user3 = User("Taeho", "[email protected]", "123abc")
user4 = User("Lisa", "[email protected]", "abc123")
print(user1.email)
print(user2.name)
print(user3.password)
➡ __str__ 메소드
-
print
함수를 호출할 때 자동으로 호출됨 -
return 값을 출력
-
원하는 정보를 나오게 할 때 사용
class User:
def __init__(self, name, email, pw):
self.name = name
self.email = email
self.pw = pw
def __str__(self):
return "사용자: {}, 이메일: {}, 비밀번호: ******".format(self.name, self.email)
user1 = User("구자현", "[email protected]", '12345')
user2 = User("박준규", "[email protected]", "24680")
print(user1)
print(user2)
# __str__이 없다면 출력되는 저장경로
# <__main__.User object at 0x0000021303A65FD0>
# <__main__.User object at 0x0000021303A65F10>
# 사용자: 구자현, 이메일: [email protected], 비밀번호: ******
# 사용자: 박준규, 이메일: [email protected], 비밀번호: ******
➡ 클래스 변수 #1
클래스 변수란?
-
여러 인스턴스들이 공유하는 속성
-
클래스 이름 밑에 정의
class User:
count = 0
def __init__(self, name, email, pw):
self.name = name
self.email = email
self.pw = pw
User.count += 1
user1 = User('구자현','[email protected]', '12345')
user2 = User('민정호', '[email protected]', '13579')
user3 = User('박준규', '[email protected]', '24680')
print(User.count)
# 3
➡ 클래스 변수 #2
-
클래스 이름.클래스 변수 이름
으로 변수의 값을 읽는다 -
인스턴스 이름.클래스 변수 이름
으로 읽기도 가능 -
같은 이름의 클래스 변수와 인스턴스 변수가 있으면 인스턴스 변수를 읽음
헷갈릴 수 있기 때문에 클래스 변수에 값을 읽어올 때 반드시 클래스 이름으로만 ❗❗
class User:
count = 0
def __init__(self, name, email, pw):
self.name = name
self.email = email
self.pw = pw
User.count += 1
user1 = User('구자현','[email protected]', '12345')
user2 = User('민정호', '[email protected]', '13579')
user3 = User('박준규', '[email protected]', '24680')
user1.count = 5 # 같은 이름을 가진 인스턴스 변수
print(User.count)
print(user1.count)
print(user2.count)
print(user3.count)
# 3
# 5
# 3
# 3
➡ decorator
-
기존 함수에 새로운 기능 추가하는 역할
-
여러 함수에 중복되는 기능을 간결하게 하기 위함
def add_print_to(original):
def wrapper():
print('함수 시작')
original()
print('함수 끝')
return wrapper
@add_print_to # decorator
def print_hello():
print('안녕하세요!')
print_hello()
# 함수시작
# 안녕하세요!
# 함수 끝
➡ 클래스 메소드 #1
-
인스턴스 메소드 : 인스턴스 변수의 값을 읽거나 설정하는 메소드
-
클래스 메소드 : 클래스 변수의 값을 읽거나 설정하는 메소드
-
첫 번째 파라미터의 이름은 반드시 ❗❗
cls
로 쓰기
클래스 메소드는 인스턴스 메소드와 달리 첫 번째 파라미터로 클래스 자동 전달
클래스 메소드 decorator로 number_of_users를 클래스 메소드로 만들어 줬기 때문
class User:
count = 0
def __init__(self, name, email, pw):
self.name = name
self.email = email
self.pw = pw
User.count += 1
@classmethod # 클래스 메소드 decorator
def number_of_users(cls):
print("총 유저 수는: {}입니다".format(cls.count))
user1 = User('구자현','[email protected]', '12345')
user2 = User('민정호', '[email protected]', '13579')
user3 = User('박준규', '[email protected]', '24680')
User.number_of_users()
user1.number_of_users()
# 총 유저 수는: 3입니다
# 총 유저 수는: 3입니다
➡ 클래스 메소드 #2
-
number_of_users
는 인스턴스 변수를 사용하지 않기 때문에 클래스 메소드로 만듦 -
인스턴스 변수를 사용하지 않으니
self
에 접근할 필요가 없다 -
클래스 변수만 사용하는 경우 클래스 메소드로 작성해야 함
-
인스턴스 변수 사용 ➡ 인스턴스 메소드
클래스 변수 사용 ➡ 클래스 메소드
둘 다 쓴다면 ❓
인스턴스 메소드를 사용한다 ❗
👉 인스턴스 메소드는self
를 이용해 인스턴스 변수에,
클래스 이름.클래스 변수
를 이용해 클래스 변수에 접근할 수 있지만
클래스 메소드는 인스턴스 변수 접근 불가 ❗❗
class User:
count = 0
def __init__(self, name, email, pw):
self.name = name
self.email = email
self.pw = pw
User.count += 1
def number_of_users(self): # 인스턴스 메소드
print("총 유저 수는: {}입니다".format(User.count))
user1 = User('구자현','[email protected]', '12345')
user2 = User('민정호', '[email protected]', '13579')
user3 = User('박준규', '[email protected]', '24680')
User.number_of_users(user1)
user1.number_of_users()
# 총 유저 수는: 3입니다
# 총 유저 수는: 3입니다
- 인스턴스 없이도 필요한 정보가 있다면 클래스 메소드로 작성
- User.count는 인스턴스가 하나도 없더라도 필요한 정보
class User:
count = 0
def __init__(self, name, email, pw):
self.name = name
self.email = email
self.pw = pw
User.count += 1
@classmethod # 클래스 메소드
def number_of_users(cls):
print("총 유저 수는: {}입니다".format(cls.count))
User.number_of_users()
# 총 유저 수는: 0입니다
# 인스턴스가 하나도 없을 때에도 사용할 가능성이 있다면 클래스 메소드로 만들어야한다.
➡ 정적 메소드
-
인스턴스 변수, 클래스 변수를 전혀 다루지 않는 메소드
-
인스턴스, 클래스 두 가지 모두를 통해 사용 가능
-
인스턴스 변수나 클래스 변수 중 아무것도 사용하지 않을 메소드라면 정적 메소드로 만듦
class User:
count = 0
# 문자열에 @가 들어있는지 체크하는 정적 메소드
@staticmethod # decorator를 표시해야 함
def is_valid_email(email_address):
return "@" in email_address
# 클래스로 접근
print(User.is_valid_email("jahyeongu"))
print(User.is_valid_email("[email protected]"))
# 인스턴스로 접근
print(user1.is_valid_email("jahyeongu"))
print(user1.is_valid_email("[email protected]"))
# False
# True
# False
# True
Author And Source
이 문제에 관하여(TIL_26 : 객체 지향 프로그래밍), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@wumusill/TIL27-객체-지향-프로그래밍저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)