20.Python编程:类和对象
前面已经学习了面向对象和面向过程
的区别和联系,面向过程编程和面向对象编程是两种程序设计思想,是从不同角度去思考问题的。我们已经知道Python是面向对象的开发语言,其中,最重要的概念:类和对象,以及面向对象编程的特性(继承、多态、封装)。本文就来学习Python中,最基本的面向对象的知识:类和对象。
类:class
类(class): 用来描述具有相同的属性和方法的对象的集合,它定义了该集合中每个对象所共有的属性和方法。对象是类的实例。
也就是说:类是一个抽象的集合的概念,对象是一个个具体的事物。
如:人类是对人的一种抽象的集合,而张三、李四、小明、雷锋等是一个个具体的人,称为对象,也可以叫做人类的实例。
再如:手机是一个类,假如你在用手机是iPhoneX,你手中的手机是手机的一个实例,也叫手机对象;假设我在用的是小米6,我的手机也是手机类的一个实例,当然也叫手机对象。可见,一个类型的实例对象可以有任意个。
属性:可以描述该类对象的特征的静态数据;例如,定义一个狗类:Dog,身高、品种、毛色等,可以定义成Dog类中的一个个的属性: height,type,color等。
方法:该类对象的动态行为、功能的封装;例如,定义一个狗类:Dog,吃、睡觉、走路等,可以封装成对应的方法:eat()、sleep()、walk();
定义一个类
在python中,定义一个类需要关键字:class
,语法格式如下:
class ClassName(object):
<statement-1>
·
·
·
<statement-N>
说明:class后面紧接着是类名,即ClassName,类名通常是大写开头的单词。紧接着是(object),表示该类是从哪个类继承下来的,继承的概念我们后面再讲,通常,如果没有合适的继承类,就使用object类,这是所有类最终都会继承的类。<statement-1>表示类中的属性或方法。
这样我们就自定义好了一个类。
例如:定义一个Person类,代码如下:
# 定义Person 类
class Person(object):
# name 姓名属性
name = ''
# age 年龄属性
age = 1
# 打印姓名和年龄
def print_person_info(self):
print("name:", self.name, "age:", self.age)
不同的语言定义类的关键词及格式是不同的,这就像一种游戏的规则,我们既然选择python开发,就要熟悉python中一系列的规则和习惯。
实例化和对象
定义好了一个类后,就可以根据自定义的类来创建出该类型的实例,创建实例是通过类名()
实现的。类实例化后,可以使用其属性,实际上,创建一个类之后,可以通过类名访问其属性。
你也可以这么理解:对象等价于实例。根据一个类型创建一个对象的过程,叫做实例化。
例如:
# 定义Person 类
class Person(object):
# name 姓名属性
name = ''
# age 年龄属性
age = 1
# 打印姓名和年龄
def print_person_info(self):
print("name:", self.name, "age:", self.age)
# 创建一个Person类型的对象
p = Person()
# 打印变量指向的Person类型的一个对象
print(p)
运行结果:
<__main__.Person object at 0x000001F7B61B4E48>
可以看到,变量p指向的就是一个Person类型的实例,后面的0x000001F7B61B4E48是内存地址,每个对象object的地址都不一样,所以你打印出的地址和我的不同,我自己每次运行打印的结果也不同。而Person本身则是一个类。
对象创建好了,就可以根据指向对象的变量来对对象的属性赋值、调用方法等一系列操作了。如:
# 上接
p.name = "Xiao Ming"
p.age = 12
p.print_person_info()
运行结果:
<__main__.Person object at 0x0000026C61FA4B38>
name: Xiao Ming age: 12
构造函数
很多类都倾向于将对象创建为有初始状态的。因此类可能会定义一个名为 __init__()
的特殊方法(构造方法),像下面这样:
def __init__(self):
注意:
- 类定义了
__init__()
方法的话,类的实例化操作会自动调用__init__()
方法。
2.如果你也用的Pychar开发工具的话,当你在一个类中键入def __init
时,就会提示:
可以看到,__init__()
方法的第一个参数永远是self,表示创建的实例本身,因此,在__init__()
方法内部,就可以把各种属性绑定到self,因为self就指向创建的实例本身。这和Objective-C中的self含义一样,表示实例对象,而不是代表类。同样,Java中,具有相同意义的关键字是:this
。
3.有了__init__()
方法,在创建实例的时候,就不能传入空的参数了,必须传入与__init__()
方法匹配的参数,但self不需要传,Python解释器自己会把实例变量传进去。
4.和普通的函数相比,在类中定义的函数只有一点不同,就是第一个参数永远是实例变量self,并且,在调用时,不用传递该参数。除此之外,类的方法和普通函数没有什么区别,所以,你仍然可以用默认参数、可变参数、关键字参数和命名关键字参数。提示:关于参数详细的介绍,前面已经学习,如果不熟,可以去翻阅。
例如:
# 定义Person类
class Person(object):
# name 属性
name = ''
# 年龄属性
age = 1
# 构造方法
def __init__(self, name, age):
self.name = name
self.age = age
# 打印自己信息的方法
def print_person_info(self):
print("name:", self.name, "age:", self.age)
# 创建一个Person类型的对象,并把变量p指向该对象
p = Person('Xiao Ming', 12)
p.print_person_info()
# 再次创建一个Person类型的对象,并把变量p1指向该对象
p1 = Person('Zhang San', 20)
p1.print_person_info()
# 打印p,p1
print('p =', p)
print('p1 =', p1)
运行结果:
name: Xiao Ming age: 12
name: Zhang San age: 20
p = <__main__.Person object at 0x00000283308B7240>
p1 = <__main__.Person object at 0x00000283308B7470>
再次提示:
1.__init__()
函数是Python类中预定义的函数。也就是说,当以定义好了一个类时,构造函数就有了。默认的构造函数只有一个self参数。特别提醒:构造方法__init__
前后分别有两个下划线哦~
2.self代表类的实例对象本身,而非类。self 不是 python 关键字,我们把他换成任意合法标识名也是可以正常执行的,按照惯例它的名称是 self。
3.和普通的函数相比,在类中定义的函数(也包括类中预定义的函数)只有一点不同,就是第一个参数永远是实例变量self,并且,在调用时,不用传递该参数。除此之外,类的方法和普通函数没有什么区别,所以,你仍然可以用默认参数、可变参数、关键字参数和命名关键字参数。
验证:self代表类的实例,而非类
# 定义智能手机类:SmartPhone
class SmartPhone(object):
os = '' # 系统
type = '' # 品牌 属性
memory = 6 # 内存大小,单位GB
# 构造方法
def __init__(self,os, type, memory):
self.os = os
self.type = type
self.memory = memory
print('os:', os, '\n品牌:', type, '\n内存大小:', memory )
# 验证self, self.__class__
def print_self(self):
print('self :', self)
print('self.__class__:', self.__class__)
# 创建SmartPhone对象,并把变量my_phone指向该对象
my_phone = SmartPhone('Android', 'Xiao Mi 6', '6GB')
# 调用SmartPhone对象的print_self()方法
my_phone.print_self()
# 打印my_phone变量指向的SmartPhone对象的地址
print('my_phone: ', my_phone)
# 打印my_phone变量指向的SmartPhone对象的类型
print('my_phone.__class__:', my_phone.__class__)
运行结果:
os: Android
品牌: Xiao Mi 6
内存大小: 6GB
self : <__main__.SmartPhone object at 0x00000173714D7048>
self.__class__: <class '__main__.SmartPhone'>
my_phone: <__main__.SmartPhone object at 0x00000173714D7048>
my_phone.__class__: <class '__main__.SmartPhone'>
从执行结果可以很明显的看出,self 代表的是类的实例,代表当前对象的地址,而 self.class 则指向类。
说明:类和对象的关系
面向对象最重要的概念就是类(class)和实例(Instance),必须牢记类是抽象的模板,比如Person类、SmartPhone类,而实例是根据类创建出来的一个个具体的“对象”,每个对象都拥有相同的方法,但各自的数据可能不同。
属性和方法
和普通的函数相比,在类中定义的函数(也包括类中预定义的函数)只有一点不同,就是第一个参数永远是实例变量self,并且,在调用时,不用传递该参数。除此之外,类的方法和普通函数没有什么区别,所以,你仍然可以用默认参数、可变参数、关键字参数和命名关键字参数。
在类中定义好的属性,就可以赋值、取值,方法就可以调用了。
同样以SmartPhone类为例:
# 定义智能手机类:SmartPhone
class SmartPhone(object):
os = '' # 系统
type = '' # 品牌 属性
memory = 6 # 内存大小,单位GB
# 构造方法
def __init__(self, os, type, memory):
self.os = os
self.type = type
self.memory = memory
self.print_info()
# 打印手机信息
def print_info(self):
print('os:', self.os, '\n品牌:', self.type, '\n内存大小:', self.memory)
# 验证self, self.__class__
def print_self(self):
print('self :', self)
print('self.__class__:', self.__class__)
# 创建SmartPhone对象,并把变量my_phone指向该对象
my_phone = SmartPhone('Android', 'xiao mi 6', '6GB')
# 修改内存大小
my_phone.memory = "8GB"
# 修改品牌
my_phone.type = 'MeiZu 7Pro'
print('-----------')
# 调用SmartPhone对象的方法,打印手机信息
my_phone.print_info()
运行结果:
os: Android
品牌: xiao mi 6
内存大小: 6GB
-----------
os: Android
品牌: MeiZu 7Pro
内存大小: 8GB
小结
本文重点学习了Python3中的面向对象最基础的类和对象的知识:类的定义、对象、构造方法、属性和方法等。接下来会学习访问权限、继承、多态、封装等面向对象的知识,以上知识是所有面向对象必须学习的基础知识,只是不同的开发语言语法、书写格式不同而已,但这些概念几乎一致的。
更多了解,可关注公众号:人人懂编程
微信公众号:人人懂编程