Python面向对象编程

目录

一切皆对象

类与对象

数据属性和实例属性

类的方法

类的继承 

单继承:

多继承:

深度优先和广度优先: 

类的多态:

反射 

工厂设计模式 


一切皆对象

类与对象

类的关键字是:class,所有类的基类是object,定义类的时候类的首字母一定要大写!

class Person(object):
    '''定义一个人的类'''
    country = 'china' #数据属性
    def __init__(self, name, age):
        self.name = name
        self.age = age

if __name__ == '__main__':
    person1= Person(name='xia', age=18)  #person就是Person()实例化后的对象
    person2= Person(name='夏', age=19)  #person就是Person()实例化后的对象
    print(person.__dict__)  #将name='xia',age=18以字典的形式输出
    print(person.__doc__)   #输出'''定义一个人的类'''

数据属性和实例属性

数据属性:同一个类实例化后的不同的对象调用数据属性,内存地址都是一样的

person1.country和person2.country调用的内存地址是一样的

实例属性:如上栗子中在类里面定义的属性name,age被称为实例属性,定义的时候必须遵守函数的形参参数的规则,有几个参数就传几个 

类的方法

在python类里边,编写的特性函数称为方法,共分为普通方法,特性方法,静态方法,类方法

class Person(object):
    def __init__(self, name, age):
        self.name = name
        self.age = age
    
    # 普通方法
    def show(self):
        print("my name is {0} my age is {1}".format(self.name, self.age))

    @property
    def info(self):  #不能有形式参数
        print("........特性方法") 

    @staticmethod
    def eat():  #没有self和cls参数
        print("静态方法")

    @classmethod  #参数是cls
    def driver(cls):
        print("类方法")


if __name__ == '__main__':
    person = Person(name='xia', age=18)
    person.show()
    person.info #特性方法的调用类似于调用类里的数据属性,后边不带()
    Person.eat() #属于类,直接用类名调用
    Person.driver() #属于类,直接用类名调用

类的继承 

面向对象三大特性是:封装、继承、多态,一个类可以继承一个类,也可以继承多个类

子类可以继承父类所有的方法和属性

单继承:

#!/usr/bin/env python
# !coding:utf-8
class Person(object):
    '''定义一个人的类'''
    country = '中国'

    def __init__(self, name, age):
        self.name = name
        self.age = age

    def show(self):
        print("my name is {0} my age is {1}".format(self.name, self.age))


# 继承了Person类
class Worker(Person):
    def __init__(self, name, age, salary):
        super().__init__(name, age)
        self.salary = salary

    def info(self):
        print("姓名{0} 年龄{1} 薪水{2}".format(self.name, self.age, self.salary))
    
    # 如果子类没有show()方法,就会调用父类的show()方法,子类有的话直接重写show()方法
    def show(self):
        print("我是worker的show")


if __name__ == '__main__':
    worker = Worker(name='xia', age=18, salary=10000)
    worker.info()
    worker.show()
    print(worker.country)
    worker.country = '美丽国' #重写了父类的属性
    print(worker.country)


输出结果:
姓名xia 年龄18 薪水10000
我是worker的show
中国
美丽国

多继承:

#!/usr/bin/env python
# !coding:utf-8
# 顺序:继承遵循从左到右,从下到上的顺序(主要用于单继承,继承有父类,爷爷类,优先调用父类)
class Person(object):
    '''定义一个人的类'''

    def __init__(self, name, age):
        self.name = name
        self.age = age

    def show(self):
        print("my name is {0} my age is {1}".format(self.name, self.age))


class Animal:
    def __init__(self, sex):
        self.sex = sex

    def show(self):
        print("这是动物类")

# 没有show()方法就去父类里去找,先找Person类,找到就停止,没找到继续找Animal类
class Worker(Person, Animal):
    def __init__(self, name, age, salary, sex):
        super().__init__(name, age)
        Animal.__init__(self, sex)
        self.salary = salary

    def info(self):
        print("姓名{0} 年龄{1} 薪水{2} 性别{3}".format(self.name, self.age, self.salary, self.sex))

    # def show(self):
    #     print("我是worker的show")


if __name__ == '__main__':
    worker = Worker(name='xia', age=18, salary=10000, sex='女')
    worker.info()
    worker.show()

输出结果:
姓名xia 年龄18 薪水10000 性别女
my name is xia my age is 18

深度优先和广度优先: 

python2中多个类的继承算法叫深度优先,python3叫广度优先

class A:
    def show(self):
        print("A")

class B(A):
    pass

class C(A):
    def show(self):
        print("C")

class D(B, C):
    pass

if __name__ == '__main__':
    d = D()
    d.show()
# 深度优先执行顺序:先找D类,再找B类,再找A类,最后找C类
# 广度优先执行顺序:先找D类,再找B类,再找C类,最后找A类

深度优先执行顺序:

广度优先执行顺序:

类的多态:

class Animal:
    def talk(self):
        print("动物会叫")


class Cat(Animal):
    def talk(self):
        print("猫也会叫")


class Person(Animal):
    def talk(self):
        print("人也是会叫的")


def func(animal):
    animal.talk()


if __name__ == '__main__':
    # 对猫实例化
    cat = Cat()
    # 调用方式不需要修改就能拿到Cat类的信息
    func(animal=cat)
    func(animal=Person())

反射 

简单的理解为:通过字符串的形式操作对象相关的属性。涉及到的方法有setattr,getattr,hasattr,delattr

class Person:
    country = "中国"

    def __init__(self, name, age):
        self.name = name
        self.age = age

    def show(self):
        print('my name is {0},and my age is {1}'.format(self.name, self.age))


if __name__ == '__main__':
    person = Person(name="xia", age=18)
    print(hasattr(person, 'country'))  # True
    setattr(person, 'sex', '女') # 反射的新属性是字符串类型的
    delattr(person, 'sex')
    delattr(person, 'country')  # 原属性是不允许被删除的
    print(hasattr(person, 'sex'))

 反射其他模块

使用__import__就可以导入其他模块的信息

day2 :

def login():
    print('this is a login function')


def logout():
    print('this is a  logout function')
index = __import__('day2') # 导入day2模块,并赋值给字符串,字符串其实就是模块的对象
index.login()

import day2

f = getattr(day2, 'login')
f()

类案例实战 

''使用面向对象的编程方式来写一个注册,登录,查看个人主页,退出的命令行系统'''
import json
import sys


class Auth:
    def __init__(self):
        pass

    @property  #特性方法
    def input(self):
        username = input('输入用户名\n')
        pwd = input('输入密码\n')
        return username, pwd  #用到了返回值

    # 从文件中获取用户名和密码
    def login(self, username, pwd):
        temp = json.load(open('login.json', 'r'))  #反序列化读文件
        lists = temp.split('|')  #字符串的拆分变成列表
        if lists[0] == username and lists[1] == pwd:
            return True
        else:
            print("请登录")

    @property
    def register(self):
        # 将用户名和密码写入到文件中
        username, pwd = self.input
        temp = username + '|' + pwd
        json.dump(temp, open('login.json', 'w')) #序列化写文件

    @property
    def index(self):
        temp = json.load(open('login.json', 'r'))
        lists = temp.split('|')
        print("欢迎{0}进入主页".format(lists[0]))

    def exit(self):
        sys.exit(1)

    def main(self):
        while True:
            try:
                p = input('1、登录 2、注册 3、查看主页 4、退出\n')
                p = int(p)
                if p == 1:
                    username, pwd = self.input
                    isLogin = self.login(username=username, pwd=pwd)
                    if isLogin:
                        self.index  #不带()是特性方法引用时把方法当成属性
                    else:
                        self.register
                elif p == 2:
                    self.register
                elif p == 3:
                    self.index
                elif p == 4:
                    self.exit()
            except Exception as e:
                continue


if __name__ == '__main__':
    a = Auth() #类的实例化
    a.main()

工厂设计模式 

''结合工厂设计方法写一个上帝创造人的代码'''

根据不同的参数生成不同的对象,只需要知道工厂类和产品的父类,不需要关心产品的类型和创建过程

class Person:
    def __str__(self):
        return 'person'

    def showPerson(self):
        print("创造了一个人")


class Man(Person):
    def __str__(self):
        return 'man'

    def show(self):
        print("呵,男人")


class Women(Person):
    def __str__(self):
        return 'women'

    def info(self):
        print("呵,女人")


class Factory:
    def creatPerson(self, obj):
        if obj == 'man':
            return Man()
        if obj == 'women':
            return Women()


if __name__ == '__main__':
    factory = Factory()
    # 根据不同的参数生成不同的对象,只需要知道工厂类和产品的父类
    objMan = factory.creatPerson(obj='man')
    objWomen = factory.creatPerson(obj='women')
    objMan.show()
    objWomen.info()

 

 

 

 

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

菜鸟学识

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值