ν°μ€ν 리 λ·°
<λͺ©μ°¨>
π κ°μ²΄ μ§ν₯ νλ‘κ·Έλλ°(Object Oriented Programming, OOP)
π κ°μ²΄(Object)
βοΈ μ«μμμ ν¨μκΉμ§ νμ΄μ¬μ λͺ¨λ κ²μ κ°μ²΄λ€.
num = 7μ μ λ ₯νμ λ 7μ΄ λ΄κΈ΄ μ μ μ νμ κ°μ²΄λ₯Ό μμ±νκ³ κ°μ²΄ μ°Έμ‘°(object reference)λ₯Ό numμ ν λΉνλ€.
βοΈ κ°μ²΄λ λ°μ΄ν°(λ³μ, μμ±)μ μ½λ(ν¨μ, λ©μλ)λ₯Ό ν¬ν¨νλ 컀μ€ν μλ£κ΅¬μ‘°μ΄λ€.
ν¨μ : κ°μ²΄ μΈμ μ½λ λμΉ
λ©μλ : ν΄λμ€ μμ λ©€λ² μΈμ μ½λ λμΉ
βοΈ κ°μ²΄λ ꡬ체μ μΈ μ΄λ€ κ²μ μ μΌν μΈμ€ν΄μ€(instance)λ₯Ό κ°λ¦¬ν¨λ€.
βοΈ κ°μ²΄λ μ μλ ν΄λμ€λ₯Ό ν΅ν΄ μμ±λλ€. κ°μ²΄ != ν΄λμ€
π ν΄λμ€(Class)
βοΈ κ°μ²΄μ νμ λνλΈλ€.
class Cat:
pass
βοΈ Cat()μ Cat ν΄λμ€λ‘λΆν° κ°λ³ κ°μ²΄λ₯Ό μμ±νμ¬ κ°μ²΄ μ°Έμ‘°λ₯Ό a_catκ³Ό another_catμ ν λΉνλ€.
- a_catκ³Ό another_catμ κ°μ ν΄λμ€μ λ€λ₯Έ κ°μ²΄μ΄λ―λ‘ λ€λ₯΄κ² 맡νλλ€.
a_cat = Cat()
another_cat = Cat()
print(a_cat)
<__main__.Cat object at 0x000002050461D9A0>
print(another_cat)
<__main__.Cat object at 0x000002050461DD30>
π μμ±(Attribute)
βοΈ μμ±μ ν΄λμ€λ κ°μ²΄ λ΄λΆμ λ³μλ€.
βοΈ κ°μ²΄λ ν΄λμ€κ° μμ±λλ λμμλ μμ± κ°λ₯νμ§λ§ μμ± μ΄νμλ μμ±μ μΆκ° μμ±ν μ μλ€.
# Cat ν΄λμ€μ μ μΈλμ΄ μμ§ μμ μμ±μ μΆκ°λ‘ μ¬μ© κ°λ₯
a_cat.age = 3
a_cat.name = "cat"
a_cat.nemesis = another_cat
a_cat.age
Out[102]: 3
a_cat.name
Out[100]: 'cat'
a_cat.nemesis
Out[101]: <__main__.Cat at 0x2050461dd30>
π λ©μλ(Method)
βοΈ λ©μλλ ν΄λμ€ λλ κ°μ²΄μ ν¨μλ€.
βοΈ __init__() : κ°λ³ κ°μ²΄λ₯Ό μ΄κΈ°ννλ νΉμ λ©μλ
__init__() λ©μλλ λ€λ₯Έ μΈμ΄μμμ "μμ±μ"μ κ°λ μ΄ μλλ€.
__init__() λ©μλ νΈμΆ μ μ μ΄λ―Έ κ°μ²΄κ° λ§λ€μ΄μ Έ μκΈ° λλ¬Έμ΄λ€.
βοΈ self : κ°λ³ κ°μ²΄ μμ μ μ°Έμ‘°
class Cat():
def __init__(self, name):
self.name = name
self.nameμ κ²½μ° λͺ μμ μΌλ‘ ν΄λμ€μ μμ±μΌλ‘ μ μΈλμ΄ μμ§λ μμ§λ§ ν΄λμ€ λ΄μ μμ±μΌλ‘μ¨ μ¬μ© κ°λ₯νλ€.
π κ°μ²΄ μμ
π μμ(inherit)
κ°μ²΄μ μ£Όμ νΉμ± : μΊ‘μν, μμ, μΆμν, λ€νμ±
βοΈ νμν κΈ°λ₯μ κΈ°μ‘΄μ κ²μ μ¬μ©νμ!! μ¬μ¬μ©!!
- λΆλͺ¨ ν΄λμ€ : κΈ°μ‘΄μ κ²
- μμ ν΄λμ€ : νμλ κ², sub class
class Car:
pass
class Yugo(Car):
pass
βοΈ issubclass(a, b) : aκ° bμ μλΈ ν΄λμ€ μΈκ°?
issubclass(Yugo, Car)
Out[15]: True
π‘ data typeμ μμ
boolμ intμ μλΈ ν΄λμ€μ΄λ€. = boolμ intλ₯Ό μμλ°λλ€.
issubclass(bool, int)
Out[21]: True
issubclass(int, bool)
Out[23]: False
issubclass(int, float)
Out[22]: False
issubclass(float, int)
Out[25]: False
isinstance()
π μμ ν΄λμ€
βοΈ λΆλͺ¨ ν΄λμ€μ νΉμ§μ κ°μ Έμ¬ μ μλ€. (= μμ λ°λλ€.)
νΉμ§ : λ©μλ, λ©€λ², λμ κ³Όμ λ±
class Car():
def exclaim(self):
print("I am a Car!")
class Yugo(Car):
pass
give_me_a_car = Car()
give_me_a_yugo = Yugo()
give_me_a_car.exclaim()
I am a Car!
give_me_a_yugo.exclaim()
I am a Car!
βοΈ μμ ν΄λμ€λ§μ μλ‘μ΄ κΈ°λ₯μ μ μν μ μλ€.
λ©μλ λͺ μ΄ μλ‘λ€λ©΄ μλ‘κ² μ μλκ³ , λ©μλ λͺ μ΄ κ°λ€λ©΄ μ¬μ μ(override) λλ€.
π μ€λ²λΌμ΄λ(override, μ¬μ μ)
override vs overload
class Car():
def exclaim(self):
print("I am a Car!")
class Yugo(Car):
def exclaim(self):
print("I am a Yugo!")
give_me_a_car = Car()
give_me_a_yugo = Yugo()
give_me_a_car.exclaim()
I am a Car!
give_me_a_yugo.exclaim()
I am a Yugo!
βοΈ __init__() λ©μλλ μ€λ²λΌμ΄λ λλ€.
class Person:
def __init__(self, name):
self.name = name
class MDPerson(Person):
def __init__(self, name):
self.name = "Doctor " + name
class JDPerson(Person):
def __init__(self, name):
self.name = name + ", Esquire"
person = Person("Riri")
doctor = MDPerson("Riri")
lawyer = JDPerson("Riri")
person.name
Out[53]: 'Riri'
doctor.name
Out[52]: 'Doctor Riri'
lawyer.name
Out[54]: 'Riri, Esquire'
π Super()
βοΈ μμλ°μ κ°μ²΄κ° λΆλͺ¨ κ°μ²΄λ₯Ό μμ²ν λ μ¬μ©νλ€.
βοΈ λΆλͺ¨ ν΄λμ€μ μ μλ₯Ό μ»μ΄μ¨λ€.
βοΈ super().__init__(name)
λΆλͺ¨ ν΄λμ€μ nameμ μΈμλ‘ λ°μμ¨ nameμΌλ‘ μ΄κΈ°ν ν΄μ€λ€.
→ μμ ν΄λμ€μμ __init__() λ©μλλ₯Ό μ€λ²λΌμ΄λ ν΄μ μ¬μ©νκΈ° λλ¬Έμ μ΄λ₯Ό μ°μ§ μμΌλ©΄ λΆλͺ¨ ν΄λμ€μ __init__() ν¨μκ° μ€νλμ§ μκΈ° λλ¬Έμ μ¬μ©ν΄μΌνλ€.
class Person:
def __init__(self, name):
self.name = name
class EmailPerson(Person):
def __init__(self, name, email):
super().__init__(name)
self.email = email
bob = EmailPerson("Bob Frapples", "bob@frapples.com")
bob.name
Out[31]: 'Bob Frapples'
bob.email
Out[32]: 'bob@frapples.com'
π λ€μ€ μμ
βοΈ κ°μ²΄λ μ¬λ¬ λΆλͺ¨ ν΄λμ€λ₯Ό μμλ°μ μ μλ€.
class Animal:
def says(self):
return "I speak"
class Horse(Animal):
def says(self):
return "Neigh"
class Donkey(Animal):
def says(self):
return "Hee-haw"
class Mule(Donkey, Horse):
pass
class Hinny(Horse, Donkey):
pass
π‘ λ©μλ ν΄μ μμ - mro()
λ€μκ³Ό κ°μ μμλ‘ ν΄λμ€μμ λ©μλλ μμ±μ μ°Ύλλ€.
κ°μ²΄ μμ → κ°μ²΄μ ν΄λμ€ → 첫λ²μ§Έ λΆλͺ¨ ν΄λμ€ → λλ²μ§Έ λΆλͺ¨ ν΄λμ€ → λΆλͺ¨ ν΄λμ€
Mule.mro()
Out[34]: [__main__.Mule, __main__.Donkey, __main__.Horse, __main__.Animal, object]
Hinny.mro()
Out[35]: [__main__.Hinny, __main__.Horse, __main__.Donkey, __main__.Animal, object]
mule = Mule()
hinny = Hinny()
mule.says()
Out[43]: 'Hee-haw'
hinny.says()
Out[44]: 'Neigh'
π λ―Ήμ€μΈ / μ»΄ν¬μ§μ
π κ°μ²΄ μμ± μ κ·Ό - μΊ‘μν
Python vs Java
π μ§μ μ κ·Ό
βοΈ νμ΄μ¬μ μΌλ°μ μΌλ‘ κ°μ²΄ μμ±κ³Ό λ©μλκ° κ³΅κ°λμ΄ μμ΄ μ§μ μ κ·Όμ΄ κ°λ₯νλ€.
βοΈ νμ§λ§ λ€μκ³Ό κ°μ΄ ν΄λμ€ μΈλΆμμ λ³Ό μ μλλ‘ μ ν ν μμ±(private attribute)μλ μ κ·Όνμ§ λͺ»νλ€.
class Blink():
def __init__(self, input_name, input_pw):
self.name = input_name
self.__password = input_pw
blink = Blink("Riri", "ilovelisa")
blink.name
Out[84]: 'Riri'
blink.__password
Traceback (most recent call last):
File "C:\Anaconda\lib\site-packages\IPython\core\interactiveshell.py", line 3437, in run_code
exec(code_obj, self.user_global_ns, self.user_ns)
File "<ipython-input-85-94be706f037f>", line 1, in <module>
blink.__password
AttributeError: 'Blink' object has no attribute '__password'
blink.password
Traceback (most recent call last):
File "C:\Anaconda\lib\site-packages\IPython\core\interactiveshell.py", line 3437, in run_code
exec(code_obj, self.user_global_ns, self.user_ns)
File "<ipython-input-86-122aad938aa4>", line 1, in <module>
blink.password
AttributeError: 'Blink' object has no attribute 'password'
π‘ λ€μ λ§ΉκΈλ§(name mangling)
ν΄λμ€ μ μλ₯Ό μΈλΆμμ λ³Ό μ μλλ‘ νλ μμ±μ λν λ€μ΄λ° 컨벀μ (naming convention)μ΄λ€.
- μμ± μ΄λ¦ μμ λ μΈλλ°(__)λ‘ μ μ©
- μμ±μ μλμ μΈ μ§μ μ κ·Όμ μ΄λ ΅κ² λ§λ λ€.
- private attribute : λλ²κΉ ν λ 보μ΄μ§ μλλ€. = λ°νμμμ 보μ΄μ§ μλλ€.
λ€μκ³Ό κ°μ λ°©μμΌλ‘ μ κ·Όν μ μλ€.
blink._Blink__password
Out[93]: 'ilovejisso'
π Getter/Setter λ©μλ
class Blink():
def __init__(self, input_name, input_pw):
self.name = input_name
self.__password = input_pw
def get_pw(self):
print("inside the getter")
return self.__password
def set_pw(self, input_pw):
print("inside the setter")
self.__password = input_pw
blink = Blink("Riri", "ilovelisa")
blink.name
Out[75]: 'Riri'
blink.get_pw()
inside the getter
Out[76]: 'ilovelisa'
blink.set_pw("ilovejennie")
inside the setter
blink.get_pw()
inside the getter
Out[78]: 'ilovejennie'
π νλ‘νΌν° (@property)
class Blink():
def __init__(self, input_name, input_pw):
self.name = input_name
self.__password = input_pw
@property
def password(self):
print("inside the getter")
return self.__password
@password.setter
def password(self, input_pw):
print("inside the setter")
self.__password = input_pw
blink = Blink("Riri", "ilovelisa")
blink.name
Out[89]: 'Riri'
blink.password
inside the getter
Out[90]: 'ilovelisa'
blink.password = "ilovejisso"
inside the setter
blink.password
inside the getter
Out[92]: 'ilovejisso'
π‘ κ³μ°λ κ°μ νλ‘νΌν°
νλ‘νΌν°λ κ³μ°λ κ°(computed value)λ₯Ό μ°Έμ‘°ν μ μλ€.
class Circle:
def __init__(self, radius):
self.radius = radius
@property
def diameter(self):
return 2 * self.radius
c = Circle(5)
c.radius
Out[105]: 5
c.diameter
Out[106]: 10
c.radius = 7
c.diameter
Out[108]: 14
# seter propertyλ₯Ό λͺ
μνμ§ μμΌλ©΄ μΈλΆλ‘λΆν° μ΄ μμ±μ μ€μ ν μ μλ€.
c.diameter = 28
Traceback (most recent call last):
File "C:\Anaconda\lib\site-packages\IPython\core\interactiveshell.py", line 3437, in run_code
exec(code_obj, self.user_global_ns, self.user_ns)
File "<ipython-input-109-23b5625e22cc>", line 1, in <module>
c.diameter = 28
AttributeError: can't set attribute
π λ©μλ νμ
π μΈμ€ν΄μ€ λ©μλ
π ν΄λμ€ λ©μλ
@classmethod
맀κ°λ³μλ₯Ό clsλ‘ μ¬μ©
class A:
count = 0
def __init__(self):
A.count += 1
def exclaim(self):
print("I am an A!")
@classmethod
def kids(cls):
print(f"A has {cls.count} little objects")
easy_a = A()
breezy_a = A()
wheezy_a = A()
A.kids()
A has 3 little objects
π μ μ λ©μλ
βοΈ ν΄λμ€λ₯Ό ν΅ν κ°μ²΄ μμ±μ΄ νμ μλ€.
→ κ°μ²΄ μμ±μ λ¬΄κ±°μ΄ μ°μ°!!
class CoyoteWeapon:
@staticmethod
def commercial():
print("This coyoteweapon has been what?")
CoyoteWeapon.commercial()
This coyoteweapon has been what?
π λνμ΄ν
μ¬λ¦Όμ΄ μ€λ¦¬μ²λΌ νλνλ©΄ μ€λ¦¬λ‘ λ΄λ 무방νλ€λ κ°λ
βοΈ νμ μ 미리 μ νμ§ μκ³ λ°νμμ ν΄λΉ λ©μλλ€μ νμΈνλ©° κ²°μ νλ€.
π‘ λ€νμ±
νλμ κ°μ²΄κ° μ¬λ¬ κ°μ§ νμ μ κ°μ§ μ μλ κ²
νμ΄μ¬μ λ€νμ±μ λμ¨νκ² κ΅¬ννλ€.
ν΄λμ€μ μκ΄ μμ΄ κ°μ λμμ λ€λ₯Έ κ°μ²΄μ μ μ©ν μ μλ€.
class Parrot:
def fly(self):
print("Parrot flying")
class Airplane:
def fly(self):
print("Airplane flying")
class Whale:
def swim(self):
print("Whale swimming")
def lift_off(entity):
entity.fly()
βοΈ λ€ λ€λ₯΄κ² λμνλ€.
parrot = Parrot()
airplane = Airplane()
whale = Whale()
lift_off(parrot)
Parrot flying
lift_off(airplane)
Airplane flying
lift_off(whale)
Traceback (most recent call last):
File "C:\Anaconda\lib\site-packages\IPython\core\interactiveshell.py", line 3437, in run_code
exec(code_obj, self.user_global_ns, self.user_ns)
File "<ipython-input-12-d95e9c850c52>", line 1, in <module>
lift_off(whale)
File "<ipython-input-8-4c503ff8deae>", line 14, in lift_off
entity.fly()
AttributeError: 'Whale' object has no attribute 'fly'
λ§€μ§ λ©μλ
__<func>__
round ν¨μ
floor λ°λ₯ ν¨μ
ceil μ²μ₯ ν¨μ
μ 그리κ²μ΄μ / μ½€νΌμ§μ
μμμ ν΅ν΄ κΈ°λ₯μ λ¬Όλ €λ°λκ²μ΄ μλ μ κ·Ό λ°©λ²
λ―Ήμ€μΈ
λ€μ€ μμμ 볡μ‘μ±μ ν΄μνκΈ° μν λ°©λ²
λ체μ μΌλ‘ μ 그리κ²μ΄μ / μ½€νΌμ§μ μ νμ©
λ―Ήμ€μΈ (is-a) μ 그리κ²μ΄μ / μ½€νΌμ§μ (has-a)
ν΄λμ€ λ΄μ κ°μ²΄λ₯Ό μ½μ
λ€μλ νν
Dataclassκ° λ±μ₯νκΈ° μ μ νμ©λλ νμ
Ref.
- 2021 μ²λ μ·¨μ μμΉ΄λ°λ―Έ νμ΄μ¬ μμ
- μ²μ μμνλ νμ΄μ¬, λΉ λλ°λ ΈλΉ
'Python' μΉ΄ν κ³ λ¦¬μ λ€λ₯Έ κΈ
[Python/Flask] DB μ μ΄ λͺ λ Ήμ΄ (0) | 2021.07.17 |
---|---|
[Python] secrets λΌμ΄λΈλ¬λ¦¬ : Generate secure random number (0) | 2021.07.17 |
[Python] ν¨μ (Function) (1) | 2021.07.16 |
[Python/Flask] SocketμΌλ‘ λͺ¨λν° μ€ν¬λ¦° 곡μ (0) | 2021.07.15 |
[Python/Flask] HTTP POST λ°©μμΌλ‘ λͺ¨λν° μ€ν¬λ¦° 곡μ (0) | 2021.07.15 |