Python是一种面向对象(OOP)的语言,面向对象最重要的概念就是类(class)和实例(instance),必须牢记类是抽象的模板,比如整数类型,代表所有整数,而实例是根据类创建出来的一个个具体的“对象”,每个对象都拥有相同的方法,但各自的数据可能不同。

Python使用class定义一个类,我们以人为例定义一个People类。

class People:

    '''

这里是People类的文档

    '''

sex = '男' # People类具有性别属性,并且默认是男

 

    def __init__(self, name):

        '''

类进行实例化调用此初始化函数

        '''

        self.name = name

 

    def set_age(self, age):

        '''

设置一个人的年龄

        '''

        self.age = age

 

    def get_age(self):

        '''

获取一个人的年龄

        '''

函数判断一个类是否具有某属性

            return self.age

        else:

未设置年龄,请先调用set_age设置年龄')

            return None

 

    def get_sex(self):

        '''

获取这个人的性别

        '''

的性别是' + self.sex)

        return self.sex

 

    def speak(self, msg):

        '''

让这个人说一句话

        '''

说: ' + str(msg))

xiaoming = People('小明') # 实例化类People的一个对象小明

 

需要详述的是类中函数的参数self。首先明确类和对象两个概念,类表示的抽象,是一个类型,比如我们定义的People类;对象是类的一个实例,比如上面代码的xiaoming,所以在定义类时分为类本身就具有的东西,比如People类的属性sex,另一种在实例化后才有的东西,比如name,age等,而self就是指的实例化后的对象xiaoming。

 

xiaoming = People('小明') # 实例化类People的一个对象小明

# 调用类本身的属性sex

print(People.sex) # 正常获取性别

# print(People.name) 由于name是实例化才有的属性,该调用出错

print(xiaoming.sex) # 对象是具有类的属性的,正常

# 类中函数具有self的方法都是实例方法,对象才可以正常调用

xiaoming.set_age(29) # 正常设置小明的年龄

#People.set_age(29) # 报错

 

获取与设置属性

xiaoming.age = 20 # 通过实例对象设置年龄

print(xiaoming.age) # 通过实例对象获取年龄

xiaoming.sex = '女' # 通过实例对象设置性别

print(xiaoming.sex) # 通过实例对象获取性别

xiaoming.height = 178 # 给对象新建一个身高属性等于178

print(xiaoming.height) # 获取新建的属性

 

调用对象方法

xm_age = xiaoming.get_age() # 通过对象方法获取年龄

print(xm_age)

xiaoming.speak('我在学习Python')

 

继承

现在已经定义了人这个类,我们想要再具体一点定义出男和女两个类,因为这个类都属于人类,所以可以使用继承,就不用再实现人所共有的属性和方法。

class Man(People):

男'

 

class Women(People):

女'

 

xiaohong = Women('小红') # 实例化一个Women小红

xiaohei = Man('小黑') # 实例化一个Man小黑

print(xiaohong.get_sex()) # 调用小红的获取性别方法,由于子类未实现该方法,则会调用父类的

print(xiaohei.get_sex()) # 调用小黑的获取性别方法

print(isinstance(xiaohei, Man)) # 使用isinstance函数判断xiaohei是否是Man的实例

print(isinstance(xiaohei, People)) # 由于Man继承自People,所以xiaohei也是People的实例

print(issubclass(Man, People)) # 使用issubclass判断Man是否是People的子类

 

此时Man和Women就是继承自People,称为People的子类。使用继承时需注意,调用子类对象的方法时,若子类未实现,则会传递到父类调用父类的方法,而子类若是实现了与父类相同名称的方法,则会调用子类的方法,也就是子类的方法会覆盖父类方法,这种机制称为多态。

 

其他

我们对整数的运算和执行一些内置函数时,就是在调用int类的内部方法。比如str(1)就会调用int.__str__;1 + 1运算就是调用的int.__add__方法,所以我们只要在定义类时实现该方法就可以实现加法运算,以此可以想到其他的运算也是同样原理。我们现在在People末尾加入这两个方法。

 

# ……

    def __add__(self, other):

        '''

在对象进行相加操作时可以任意实现

我们使用年龄相加后返回一个新的People对象

        '''

        if isinstance(other, People):

            if hasattr(self, 'age')  and hasattr(other, 'age'):

                age = self.age + other.age

与' + other.name + '相加对象')

                new_people.set_age(age)

                return new_people

            else:

请检查年龄是否设置')

        else:

人不能与非人对象相加')

            return None

    def __str__(self):

的性别是'+self.sex

        if hasattr(self, 'age'):

年龄是' + str(self.age)

        return info

 

xiaozi = People('小紫') # 实例化一个People对象小紫

xiaolan = People('小蓝') # 实例化一个People对象小蓝

#zilan = xiaozi+xiaolan # 作加法,由于没有设置年龄返回空值

xiaozi.set_age(24)

xiaolan.set_age(26)

zilan = xiaozi+xiaolan

print(zilan) # 小紫与小蓝相加对象的性别是男, 年龄是50

 

对于数学运算,逻辑运算与一些内置函数调用等,在对象内部都可以自定义实现。

算术运算:__add__、__sub__、__mul__、__div__等

比较运算:__lt__、 __gt__等

其他:__str__、__bool__等