类和对象
-
类 - 拥有相同功能,相同的属性的对象的集合(抽象概念)
-
对象 - 对象是类的实例(具体的事物)
创建类和对象
创建类
-
用代码描述清楚这个类是拥有哪些相同的功能(函数)和哪些相同属性(变量)的对象的集合。
-
语法:
class 类名: 类的说明文档 类的类容
-
说明
-
class | : - 关键字;固定写法
-
类名
-
程序员自己命名;
-
要求:标识符、不是关键字;
-
规范:见名知义,驼峰式命名,并且第一个字母大写;不适用系统的函数名、类名、模块名;
-
-
类的说明文档 - 多行注释
-
类的内容
- 包含属性和方法;
- 属性:类属性(类的字段)、对象属性
- 方法:定义在类中的函数(对象方法、类方法、静态方法)
-
创建对象
-
语法:
语法: 类名()
# 创建人类
class Human:
"""类的说明文档"""
# 属性
# 方法
def eat(self):
print('干饭!')
# 创建对象
h1 = Human()
print(h1)
h2 = Human()
print(h2)
__init__方法 - 初始化方法
- 构造方法:
- 函数名和类名相同,用来创建对象的函数就是构造函数(构造方法)
- python的构造函数,不需要程序猿自己写,创建类的时候系统会自动创建这个类的构造函数
- 初始化方法:
- 当通过类创建对象的时候,系统会自动调用__init__方法,创建一个对象,调用一次;
- 在调用构造函数创建对象的时候,是否需要参数看对应的__init__除了self以外有没有其他参数,有其他参数就需要传对应数量的参数。
- 程序员在类中添加__init__方法的时候只需要保证方法名与默认参数self就行;(语法上来说)其他形参与函数体可以随便添加;
- 补充:方法名前后都有两个下划线的方法又叫魔法方法,这类方法不需要程序员去调用,在特定情况下会被自动调用;
class Dog:
def __init__(self):
print('创建对象')
pass
d1 = Dog() # 会自动调用__init__方法
d2 = Dog()
属性
- 定义在类中的变量
类属性
- 直接定义在类中的变量
- 变量的值不会因为对象不同而不一样
- 使用:‘类.属性名’
对象属性
-
以’self.属性名 = 值’的形式定义在__init__方法中
-
属性值会因为对象不同而不一样的时候就使用对象属性
-
在对象方法中使用对象属性
- 如果在实现对象方法的功能的时候需要用到对象属性,由self来提供对象属性
-
使用: 以’对象.属性名’的方式使用
class Circle:
a = 10 # a就是类属性
pi = 3.1415926
def __init__(self):
# radius就是一个对象属性
self.radius = 3
# 使用类属性
print(Circle.a) # 10
# 使用对象属性
c1 = Circle()
print(c1.radius) # 3
# 对象属性的初始值
class Human:
def __init__(self, name, gender='男'):
self.name = name
self.gender = gender
self.age = 0
h1 = Human('小明')
print(h1.name, h1.gender, h1.age) # 小明 男 0
h2 = Human('小红', gender='女')
print(h2.name, h2.gender, h2.age) # 小红 女 0
# 在对象方法中使用对象属性
class Circle:
pi = 3.1415926 # pi就是类属性
def __init__(self, radius):
# radius就是一个对象属性
self.radius = radius
def circle_area(self):
# 如果在实现对象方法的功能的时候需要用到对象属性,由self来提供对象属性
return Circle.pi * self.radius ** 2
def circumference(self):
return 2 * Circle.pi * self.radius
c1 = Circle(3)
print(c1.circle_area()) # 12.5663704
print(f'{c1.circumference():.2f}')
方法
- 定义在类中的函数
- 对象方法
- 定义:直接定义在类中
- 调用:对象.对象方法
- 特点:默认参数self,不用传参,self指向调用该方法的对象
- 使用时机:如果实现函数的功能需要用到对象属性,就定义为对象方法
- 类方法
- 定义:定义函数前加装饰器 @classmethod
- 调用:类.类方法
- 特点:有个默认参数cls,调用类方法时不用传参,系统自动将当前类传给cls
- 使用时机:在不需要对象属性的前提下,需要类
- 静态方法
- 定义:定义函数钱加装饰器@staticmethod
- 调用:类.静态方法
- 特点:没有默认参数
- 使用时机:在不需要对象属性的前提下,不需要类
class Student:
# study就是一个对象方法
def study(self):
print(f'self:{self}')
print('学习!')
def eat(self, food):
print(f'吃:{food}')
stu1 = Student() # self:<__main__.Student object at 0x0000023BBA3F4B20>
print(f'stu1:{stu1}') # stu1:<__main__.Student object at 0x0000023BBA3F4B20>
stu1.study()
stu1.eat('米饭')
class Dog:
@classmethod
def eat(cls):
print(f'cls:{cls}')
print('类方法')
b = cls()
print(f'b:{b}')
@staticmethod
def drink():
pass
a = Dog()
a.eat()
print(f'Dog:{Dog}')
作业
-
定义一个狗类和一个人类:
狗拥有属性:姓名、性别和品种 拥有方法:叫唤
class Dog: def __init__(self, name, breed, gender='雌'): self.name = name self.gender = gender self.breed = breed def bark(self): return f'名字叫 {self.name} 的{self.breed}{self.gender}狗叫声是:汪汪汪!' dog1 = Dog('小黄', '拉布拉多') print(dog1.bark())
人类拥有属性:姓名、年龄、狗 拥有方法:遛狗
class Human: def __init__(self, name, age, dog): self.name = name self.age = age self.dog = dog def walk_dog(self): return f'{self.age}岁的{self.name}带着名叫{self.dog}的狗在遛' h1 = Human('吴亦凡', 99, dog1.name) print(h1.walk_dog())
-
定义一个矩形类,拥有属性:长、宽 拥有方法:求周长、求面积
class RectAngle: def __init__(self, length, width): self.length = length self.width = width def perimeter(self): return (self.length + self.width) * 2 def area(self): return self.length * self.width
-
定义一个二维点类,拥有属性:x坐标、y坐标 拥有方法:求当前点到另外一个点的距离
class TwoDimensionalPoint: def __init__(self, x, y): self.x = x self.y = y def distance(self, oth_poi: tuple): return ((self.x - oth_poi[0]) ** 2 + (self.y - oth_poi[1]) ** 2) ** 0.5 p2 = (4, 5) p1 = TwoDimensionalPoint(2, 3) print(f'当前点到点:{p2}的距离为:{p1.distance(p2):.2f}')
-
定义一个圆类,拥有属性:半径、圆心 拥有方法:求圆的周长和面积、判断当前圆和另一个圆是否外切
class Circle: pi = 3.1415926 def __init__(self, cir_cen: tuple, r): self.cir_cen_x = cir_cen[0] self.cir_cen_y = cir_cen[1] self.r = r def perimeter(self): return Circle.pi * self.r * 2 def area(self): return Circle.pi * self.r ** 2 def circumscribe(self, oth_cir: tuple, oth_r): if (self.cir_cen_x - oth_cir[0]) ** 2 + (self.cir_cen_y - oth_cir[1]) ** 2 == (self.r + oth_r) ** 2: return True return False cir = Circle((0, 0), 1) print(f'圆的周长为:{cir.perimeter():.2f}') print(f'圆的面积为:{cir.area():.2f}') cir2_poi = (2, 0) cir2_r = 1 cir2 = cir.circumscribe(cir2_poi, cir2_r) print(f'与半径为{cir2_r},圆心为:{cir2_poi}的圆外切:{cir2}')
-
定义一个线段类,拥有属性:起点和终点, 拥有方法:获取线段的长度
class Line: def __init__(self, start: tuple, end: tuple): self.start_x = start[0] self.start_y = start[1] self.end_x = end[0] self.end_y = end[1] def line_length(self): return ((self.start_x - self.end_x) ** 2 + (self.start_y - self.end_y) ** 2) ** 0.5 line1 = Line((2, 3), (6, 7)) print(f'该线段的长度为:{line1.line_length():.2f}')