欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

Python面向对象的编程

程序员文章站 2022-03-18 14:33:16
在上一章节中,看书自学python-socket编程里面发现很多问题,一个重点是不知道python的class是什么,总是在百度每一句代码是什么意思,发现好像问题挺大的,万一后面还出现了class怎么办,难道每一句百度???,果断百度“python面向对象编程”,以下是学习python面向对象编程的 ......

在上一章节中,看书自学python-socket编程里面发现很多问题,一个重点是不知道python的class是什么,总是在百度每一句代码是什么意思,发现好像问题挺大的,万一后面还出现了class怎么办,难道每一句百度???,果断百度“python面向对象编程”,以下是学习python面向对象编程的一些心得,原文来自武沛齐,很多地方自己改了一下

 

大纲

1、创建类和对象

2、面向对象的三大特性

 

创建类和对象

面向对象编程是一种编程方式,此编程方式的落地需要使用 “类” 和 “对象” 来实现,所以,面向对象编程其实就是对 “类” 和 “对象” 的使用。

  类就是一个模板,模板里可以包含多个函数,函数里实现一些功能

  对象则是根据模板创建的实例,通过实例对象可以执行类中的函数

  从知乎上面看到这样一句话,不知道是对是错,反正我理解不了,感觉太高深

“实例就是对象在内存中开辟了空间。
父母口中的女朋友(对象),怀里搂着的她(实例)。”

创建一个类:

# 创建类
class Foo:
  #类中定义的函数叫方法 def Bar(self):  #类中的函数第一个参数必须是self print("bar") def Hello(self, name): print("i am %s" % name) # 根据类Foo创建对象obj obj = Foo() # 相当于拿到类里面的所有方法(函数),当然,这是我自己得理解 # Foo().Bar() obj.Bar() # 执行Bar方法 obj.Hello("smelond") # 执行Hello方法

# 面向对象:【创建对象】【通过对象执行方法】
# 函数编程:【执行函数】

 

面向对象三大特性

 

一、封装

封装,顾名思义就是将内容封装到某个地方,以后再去调用被封装在某处的内容。

所以,在使用面向对象的封装特性时,需要:

将内容封装到某处 从某处调用被封装的内容

 

第一步:将内容封装到某处

# 创建类
class Foo:
    def __init__(self, name, age):  # 称为构造方法,根据类创建对象时自动执行
        self.name = name
        self.age = age


# 根据类Foo创建对象
#  自动执行Foo类的__init__方法
obj1 = Foo("wupeiqi", 18)  # 将wupeiqi和16分别封装到(obj1、self)的name和age属性中

# 根据类Foo创建对象
#  自动执行Foo类的__init__方法
obj2 = Foo("smelond", 16)  # 将smelond和16分别封装到(obj2、self)的name和age属性中

 self 是一个形式参数,当执行 obj1 = Foo('wupeiqi', 18 ) 时,self 等于 obj1

                              当执行 obj2 = Foo('alex', 78 ) 时,self 等于 obj2

所以,内容其实被封装到了对象 obj1 和 obj2 中,每个对象中都有 name 和 age 属性,在内存里类似于下图来保存。

Python面向对象的编程

 

 第二步:从某处调用被封装的内容

调用被封装的内容时,有两种情况:

通过对象直接调用 通过self间接调用

1、通过对象直接调用被封装的内容

调用方式:对象.属性名

通过上面的代码直接调用封装的内容
print(obj1.name)
print(obj1.age)
print(obj2.name)
print(obj2.age)

输出
wupeiqi
18
smelond
16

 2、通过self间接调用被封装的内容

# 通过self间接调用
class Foo:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def detail(self):
        print(self.name)
        print(self.age)


obj1 = Foo('wupeiqi', 18)
obj1.detail()  # Python默认会将obj1传给self参数,即:obj1.detail(obj1),所以,此时方法内部的 self = obj1,即:self.name 是 wupeiqi ;self.age 是 18

obj2 = Foo('smelond', 16)
obj2.detail()  # Python默认会将obj2传给self参数,即:obj2.detail(obj2),所以,此时方法内部的 self = obj2,即:self.name 是 smelond ; self.age 是 17

输出:
wupeiqi
18
smelond
16

 综上所述,对于面向对象的封装来说,其实就是使用构造方法将内容封装到 对象 中,然后通过对象直接或者self间接获取被封装的内容。

 

练习

在终端输出如下信息

小明,10岁,男,上山去砍柴 小明,10岁,男,开车去东北 小明,10岁,男,最爱大保健 老李,90岁,男,上山去砍柴 老李,90岁,男,开车去东北 老李,90岁,男,最爱大保健 老张... Python面向对象的编程
def kanchai(name, age, gender):
    print "%s,%s岁,%s,上山去砍柴" %(name, age, gender)


def qudongbei(name, age, gender):
    print "%s,%s岁,%s,开车去东北" %(name, age, gender)


def dabaojian(name, age, gender):
    print "%s,%s岁,%s,最爱大保健" %(name, age, gender)


kanchai('小明', 10, '男')
qudongbei('小明', 10, '男')
dabaojian('小明', 10, '男')


kanchai('老李', 90, '男')
qudongbei('老李', 90, '男')
dabaojian('老李', 90, '男')
函数式编程 Python面向对象的编程
class Foo:
    
    def __init__(self, name, age ,gender):
        self.name = name
        self.age = age
        self.gender = gender

    def kanchai(self):
        print "%s,%s岁,%s,上山去砍柴" %(self.name, self.age, self.gender)

    def qudongbei(self):
        print "%s,%s岁,%s,开车去东北" %(self.name, self.age, self.gender)

    def dabaojian(self):
        print "%s,%s岁,%s,最爱大保健" %(self.name, self.age, self.gender)


xiaoming = Foo('小明', 10, '男')
xiaoming.kanchai()
xiaoming.qudongbei()
xiaoming.dabaojian()

laoli = Foo('老李', 90, '男')
laoli.kanchai()
laoli.qudongbei()
laoli.dabaojian()
面向对象

从上可以看出如果是函数式编程,会复制很多代码,而通过面向对象,只需要将参数封装到当前对象中,通过self去间接调用取值即可。

 

二、继承

继承,面向对象中的继承和现实生活中的继承相同,即:子可以继承父的内容。

例如:

  猫可以:喵喵叫、吃、喝、拉、撒

  狗可以:汪汪叫、吃、喝、拉、撒

如果我们要分别为猫和狗创建一个类,那么就需要为 猫 和 狗 实现他们所有的功能,如下所示:

Python面向对象的编程
class 猫:

    def 喵喵叫(self):
        print '喵喵叫'

    def 吃(self):
        # do something

    def 喝(self):
        # do something

    def 拉(self):
        # do something

    def 撒(self):
        # do something

class 狗:

    def 汪汪叫(self):
        print '喵喵叫'

    def 吃(self):
        # do something

    def 喝(self):
        # do something

    def 拉(self):
        # do something

    def 撒(self):
        # do something
伪代码

上述代码不难看出,吃、喝、拉、撒是猫和狗都具有的功能,而我们却分别的猫和狗的类中编写了两次。如果使用 继承 的思想,如下实现:

  动物:吃、喝、拉、撒

     猫:喵喵叫(猫继承动物的功能)

     狗:汪汪叫(狗继承动物的功能)

Python面向对象的编程
class 动物:

    def 吃(self):
        # do something

    def 喝(self):
        # do something

    def 拉(self):
        # do something

    def 撒(self):
        # do something

# 在类后面括号中写入另外一个类名,表示当前类继承另外一个类
class 猫(动物):

    def 喵喵叫(self):
        print '喵喵叫'
        
# 在类后面括号中写入另外一个类名,表示当前类继承另外一个类
class 狗(动物):

    def 汪汪叫(self):
        print '喵喵叫'
伪代码 Python面向对象的编程
class Animal:
    def eat(self):
        print("%s 吃" % self.name)

    def drink(self):
        print("%s 喝" % self.name)

    def shit(self):
        print("%s 拉" % self.name)

    def pee(self):
        print("%s 撒" % self.name)


class Cat(Animal):
    def __init__(self, name):
        self.name = name
        self.breed = "猫"

    def cry(self):
        print("喵喵叫")


class Dog(Animal):
    def __init__(self, name):
        self.name = name
        self.breed = "狗"

    def cry(self):
        print("汪汪叫 %s" % self.breed)


c1 = Cat("小白家的小黑猫")
c1.eat()
c2 = Cat("小黑家的小白猫")
c2.drink()
c3 = Dog("胖子家的小瘦狗")
c3.eat()


输出:
小白家的小黑猫 吃
小黑家的小白猫 喝
胖子家的小瘦狗 吃
代码实例

 

所以,对于面向对象的继承来说,其实就是将多个类共有的方法提取到父类中,子类仅需继承父类而不必一一实现每个方法。

注:除了子类和父类的称谓,你可能看到过 派生类 和 基类 ,他们与子类和父类只是叫法不同而已。

Python面向对象的编程