1.面向对象(类和对象)
1.编程思维
根据面对问题不同人呈现出来的思维模式不同,可以将编程思维分为三种:
1.面向过程编程(穷人思想)—— 会基本的逻辑和语法(遇到问题马上想到的是解决问题的具体逻辑和步骤);
2.函数式编程(小资思想) —— 会基本的逻辑和语法还会函数(遇到问题马上想到有没有一个已存在的函数解决这个问题,如果没有,就自己创建一个),一个函数只有一个功能;
3.面向对象编程(富豪思想) —— 会前面的两种还会类和对象 (遇到问题马上想到有没有一个具有这个功能 的对象,如果没有就创造对象),一个对象有多个功能;
2.类和对象
1.什么是类?
类具有相同的功能和相同属性的对象的集合(抽象的概念)
2.什么是对象?
对象是类的实例(是类的具体表现)
3.举例:
类:人,对象:具体的某一个人
类:车,对象:具体的某一个车,我家的灰色大众车
类:狗,对象:谁家的狗就是狗的对象
类:斗地主 对象:一场已经开始了的斗地主游戏就是斗地主的对象…
4.定义类——创建类
1.定义类:用代码来描述你的这个类是拥有哪些相同功能(用函数)和哪些相同的属性(数据,用变量)的对象的集合。
2.语法:
class 类名:
类的说明文档(类似注释)
类的内容(包含方法和属性,即函数和变量)
3.说明:
a.class —— 关键字:固定写法
b.类名 —— 由程序员自己命名
两个要求:是标识符不能是关键字
规范:见名知意;不能用系统的函数名、类名和模块名(采用驼峰式命名,必须大驼峰,首字母大写)
# user_name PEP8
# userName 小驼峰
# UserName 大驼峰
c.类的说明文档 —— 本质就是一个多行注释(可省略)
d.类的内容 —— 包含定义在类中的函数(方法)和定义在类中的变量(属性)
方法包括:对象方法,类方法,静态方法
属性包括:类属性,对象属性
4.举例:
class Dog:
"""这是狗类"""
pass
5.创建对象
1.对象是通过类来创建的。
2.语法:
类名()
class Dog:
"""这是狗类"""
pass
dog1 = Dog()
dog2 = Dog()
print(dog1) # <__main__.Dog object at 0x0000025BD165F7C0>
print(dog2) # <__main__.Dog object at 0x0000025BD165F730>
3.方法
定义在函数中的就是方法。
1.不同的方法的使用
1)对象方法
a.怎么定义:直接定义在类中的函数就是对象方法
b.怎么调用:以’ 对象.xxx(self,) '的形式来调用
c.特点:自带形参self,调用函数的时候self不需要传参,系统自动将当前对象传给self(谁调用self就指向谁)
2)类方法
a.怎么定义:定义函数前添加装饰器@classmethod
b.怎么调用:以’ 类名.xxx(csl,形参2,形参3…)'的形式来调用
c.特点:自带参数cls,调用函数的时候cls不需要传参,系统会自动将当前类传给cls
3)静态方法
a.怎么定义:定义函数前添加装饰器@staticmethod
b.怎么调用:以 ’类名.xxx()‘ 的形式来调用
c.特点:没有特点
2.怎么定义
#怎么定义
class A:
"""讲语法,无意义"""
# func1、func2是对象方法
def func1(self):
print(f'self:{self}')
print('对象方法')
def func2(self, a, b=2):
print(f'对象方法2,a:{a},b:{b}')
# func3是类方法
@classmethod
def func3(cls):
print(f'cls:{cls}') # cls:<class '__main__.A'>
print('类方法')
# func4静态方法:
@staticmethod
def func4():
print('静态方法')
# 怎么调用
a1 = A() # 需要创建一个对象
# print(a1) #括号里面self是自动加的 所以得到self=a1
a2 = A()
# 通过对象调用对象方法
a1.func1() # 对象方法 # 括号里面self是自动加的
# 实参这里是有默认的实参,系统传的,不能自己加是实参
a1.func2(10) # 对象方法2,a:10,b:2
# 但是如果自己设置了形参,那么在调用的时候就需要加入实参
# # 通过类调用类方法
# print(f'A:{A}') #A:<class '__main__.A'>
A.func3()
# 通过类调用静态方法
A.func4()
如果说写一个关于数学的类,那么就阔以使用静态方法。
class Math:
@staticmethod
def sum(n1, n2):
pass
@staticmethod
def factorial(num):
pass
4.魔法方法
1)魔法方法的特点:
a.函数名以 _ _ 开头,并且以_ _结尾
b.魔法方法不需要程序员自己调用,系统会在特地情况下自动调用
2)两个常见的魔法方法:
a. _ init :如果在类中添加了 init 方法,那么在创建当前类的对象的时候就会自动调用它
创建对象的时候需不需要实参,需要几个实参,由类中的 _ init _决定
b. repr:如果类中添加了__repr__方法,在打印类的对象的时候,会自动调用这个方法,并且将这个方法对应返回值作为打印结果进行打印。
在类中添加__repr__方法的时候,这个方法的返回值必须是字符串。
class A:
def __init__(self):
print('init方法被调用')
# 需要创建一个对象就调用了
a1 = A()
a2 = A()
class B:
def __init__(self, m, n):
print(f'm:{m},n:{n}')
def __repr__(self):
return f"<B的对象 在{hex(id(self))}>"
# 需要传参
b1 = B(10, 20) # m:10,n:20
b2 = B(m=100, n=200) # m:100,n:200
print(b1) # <B的对象 在0x2be6c62af70>
class Student():
def __init__(self, name, age=18, gender='男'):
self.name = name
self.age = age
self.gender = gender
def __repr__(self):
return f'{self.name, self.age, self.gender}'
stu1 = Student('小明')
stu2 = Student("小花", 17, '女')
print(stu2)
5.属性
定义在类中变量。
1.类属性
a.怎么定义:直接在类中定义的变量就是类属性
b.怎么使用:以’类名.xxx’的方式使用
c.什么时候用:属性不会因为对象不同而不一样就将这个属性定义成类属性
2.对象属性
a.怎么定义:直接在类中定义的变量就是类属性
b.怎么使用:以’类名.xxx’的方式使用
c.什么时候用:属性不会因为对象不同而不一样就将这个属性定义成类属性
class A:
# m、name就是类属性
m = 10
name = 'lisa'
# x,n就是对象属性
def __init__(self):
self.x = 10
self.n = 'rose'
# 通过类使用类属性
print(A.m) # 10
print(A.name) # lisa
# 通过类使用对象属性
# 先创建对象,后是用对象.xxx属性
a1 = A() # 创建对象
print(a1.x)
print(a1.n)
3.举例
类属性
class Circle:
pi = 3.1415926
def __init__(self):
self.r = 0
对象属性
class Dog:
def __init__(self, name, breed, age=3, gender='公'):
self.name = name
self.age = age
self.gender = gender
self.breed = breed
dog1 = Dog('小黑', '金毛')
dog2 = Dog('土豆', '柯基')
print(dog1.name, dog2.name)
练习:求圆的周长
class Circle:
pi = 3.1415926
def __init__(self, r=0):
self.r = r
# 如果对象方法中需要用到对象属性,由self来提供
def area(self):
return Circle.pi * self.r ** 2
def zhouchang(self):
return Circle.pi * 2 * self.r
c1 = Circle(10)
print(c1.area()) # 314.15926
print(c1.zhouchang()) # 62.831852
6.继承
**继承:**让子类直接拥有父类的属性和方法。
子类——继承者
父类——被继承的类
1.继承语法
语法
class 类名(父类列表1,父类2,父类3...):
类的说明文档
类的内容
**注意:**定义类的时候没有写父类,那么这个类会默认继承 object(基类)。
**关系:**父类拥有的东西,子类都有,但是子类除了有父类的东西以外还有一些额外特有的东西。
子类是可以继承父类所有的内容(包括:类属性、对象属性、对象方法、类方法、静态方法)。
子类中的对象属性需要加super()._ init () # 简写,调用当前类的父类的 init # super(B, self). init _()#全称
class A:
m = 100
def __init__(self):
self.n = 200
def func1(self):
print('对象方法')
@classmethod
def func2(cls):
print('类方法')
@staticmethod
def func3():
print('静态方法')
class B(A):
# 添加新的类属性
x = 'hello'
# 添加新的对象
def __init__(self):
super().__init__() # 简写,调用当前类的父类的__init__
# super(B, self).__init__()#全称,B是二字
self.p = 1000000000000
# 添加新的方法
def func11(self):
print('对象方法2')
@classmethod
def func21(cls):
print('类方法2')
@staticmethod
def func31():
print('静态方法2')
b1 = B()
# 使用A中的内容
print(B.m)
print(b1.p)
b1.func1()
B.func2()
B.func3()
# 使用B中的内容
print(B.x)
b1.func11()
B.func21()
B.func31()
print(b1.p)