类与对象

1、面向过程编程
    核心是‘过程’二字,过程指的是解决问题的步骤,即先干什么在干什么
    基于该思想编写程序就好比在编写一条流水线,是一种机械式的思维方式

    优点:复杂的问题流程化、进而简单化
    缺点:可扩展性差

2、面向对象
    核心”对象“二字,对象指的是特征与技能的结合体,
    基于该思想编写程序就好比在创造一个世界,你就是这个世界的上帝,是一种
    上帝式的思维方式

    优点:可扩展性强
    缺点:编程的复杂度高于面向过程

类与对象

1类
    对象是特征与技能的结合体,那类就是一系列对象相同的特征与技能的结合体
    
2、在现实世界中:一定先有对象,后来随着人类文明的发展总结出的类
            对象是具体存在的,而类只是一种抽象概念

3、在程序中,务必保证:先定义类,后条用类来产生对象

现实生活中的对象:
    对象1:
        特征:
            school="Oldboy"
            name="马冬梅"
            age=18
            sex="female"
        技能:
            学习
            选课

    对象2:
        特征:
            school="Oldboy"
            name="甜蜜蜜"
            age=21
            sex="male"
        技能:
            学习
            选课

    对象3:
        特征:
            school="Oldboy"
            name="原石开"
            age=22
            sex="male"
        技能:
            学习
            选课

现实生活中的老男孩学生类:
     相同的特征
            school="Oldboy"
     相同的技能
            学习
            选课
'''
# 程序中的类
class OldbouStudent:
              #用变量表示特征
              school='Oldboy'

              #用函数表示技能
              def learn(self):
                  print('is learning>>>')

              def choose(self):
                  print('choose course>>')
              print('====>')






# print(OldbouStudent.__dict__)
#====>
#注意:在定义类的阶段会立刻执行类体内的代码,然后将产生的名字存放于类名称空间中
# print(OldbouStudent.__dict__['school'])
# Oldboy

# print(OldbouStudent.__dict__['learn'])
# <function OldbouStudent.learn at 0x00000000027A97B8>

# OldbouStudent.__dict__['learn'](123)
# is learning>>>

# print(OldbouStudent.school)  #==OldbouStudent.__dict__['school']
# print(OldbouStudent.learn)  #==print(OldbouStudent.__dict__['learn'])

# OldbouStudent.learn('xxx')
# OldbouStudent.learn('>>>')
# is learning>>>
# is learning>>>

# OldbouStudent.country='China'
# OldbouStudent.school='哦的博爱'
#
# del OldbouStudent.country
# print(OldbouStudent.__dict__)
View Code
'''
1类
    对象是特征与技能的结合体,那类就是一系列对象相同的特征与技能的结合体

2、在现实世界中:一定先有对象,后来随着人类文明的发展总结出的类
            对象是具体存在的,而类只是一种抽象概念

3、在程序中,务必保证:先定义类,后条用类来产生对象

现实生活中的对象:
    对象1:
        特征:
            school="Oldboy"
            name="马冬梅"
            age=18
            sex="female"
        技能:
            学习
            选课

    对象2:
        特征:
            school="Oldboy"
            name="甜蜜蜜"
            age=21
            sex="male"
        技能:
            学习
            选课

    对象3:
        特征:
            school="Oldboy"
            name="原石开"
            age=22
            sex="male"
        技能:
            学习
            选课

现实生活中的老男孩学生类:
     相同的特征
            school="Oldboy"
     相同的技能
            学习
            选课
'''


# 程序中的类
class OldbouStudent:
              # #用变量表示特征
              # school='Oldboy'
              #
              # #用函数表示技能
              # def learn(self):
              #     print('is learning>>>')
              #
              # def choose(self):
              #     print('choose course>>')
              # print('====>')

              #   stu1 '马冬梅',18,'female'
    def  __init__(self,name,age,sex): #self=stu1  name='马冬梅’ age=18 sex=‘femal'
        self.name=name
        self.age=age
        self.sex=sex

    def learn(self):
        print('is learning。。。',self)

    def choose(self):
        print('choose course...')

# 在程序中:必须先定义类----》调用类----》对象

# 调用类发生哪些事:
# 1、首先会产生一个空对象stu1
# 2、会自动触发类内部的__init__函数
# 3、然后将空对象stu1连同调用类时括号内的参数组成(stu1,'马冬梅',18,'female'),将这四个参数一起传给__init__函数
        # 在init里面为对象添加属性 stu1.name=name
        #定制对象独有的特征 相同的特征放在类中
stu1=OldbouStudent('马冬梅',18,'female')  #OldbouStudent.__init__(stu1,'马冬梅',18,'female')
stu2=OldbouStudent("甜蜜蜜",21,'male')    #OldbouStudent.__init__(stu2,"甜蜜蜜",21,'male')
stu3=OldbouStudent("原石开",22,'male')

print(stu1.name,stu1.age,stu1.sex)
print(stu2.name,stu2.age,stu2.sex)
print(stu3.name,stu3.age,stu3.sex)

# 马冬梅 18 female
# 甜蜜蜜 21 male
# 原石开 22 male
View Code

__init__方法

#方式一、为对象初始化自己独有的特征
class People:
    country='China'
    x=1
    def run(self):
        print('----->', self)

# 实例化出三个空对象
obj1=People()
obj2=People()
obj3=People()

# 为对象定制自己独有的特征
obj1.name='egon'
obj1.age=18
obj1.sex='male'

obj2.name='lxx'
obj2.age=38
obj2.sex='female'

obj3.name='alex'
obj3.age=38
obj3.sex='female'

# print(obj1.__dict__)
# print(obj2.__dict__)
# print(obj3.__dict__)
# print(People.__dict__)





#方式二、为对象初始化自己独有的特征
class People:
    country='China'
    x=1
    def run(self):
        print('----->', self)

# 实例化出三个空对象
obj1=People()
obj2=People()
obj3=People()

# 为对象定制自己独有的特征
def chu_shi_hua(obj, x, y, z): #obj=obj1,x='egon',y=18,z='male'
    obj.name = x
    obj.age = y
    obj.sex = z

chu_shi_hua(obj1,'egon',18,'male')
chu_shi_hua(obj2,'lxx',38,'female')
chu_shi_hua(obj3,'alex',38,'female')





#方式三、为对象初始化自己独有的特征
class People:
    country='China'
    x=1

    def chu_shi_hua(obj, x, y, z): #obj=obj1,x='egon',y=18,z='male'
        obj.name = x
        obj.age = y
        obj.sex = z

    def run(self):
        print('----->', self)


obj1=People()
# print(People.chu_shi_hua)
People.chu_shi_hua(obj1,'egon',18,'male')

obj2=People()
People.chu_shi_hua(obj2,'lxx',38,'female')

obj3=People()
People.chu_shi_hua(obj3,'alex',38,'female')




# 方式四、为对象初始化自己独有的特征
class People:
    country='China'
    x=1

    def __init__(obj, x, y, z): #obj=obj1,x='egon',y=18,z='male'
        obj.name = x
        obj.age = y
        obj.sex = z

    def run(self):
        print('----->', self)

obj1=People('egon',18,'male') #People.__init__(obj1,'egon',18,'male')
obj2=People('lxx',38,'female') #People.__init__(obj2,'lxx',38,'female')
obj3=People('alex',38,'female') #People.__init__(obj3,'alex',38,'female')


# __init__方法
# 强调:
#   1、该方法内可以有任意的python代码
#   2、一定不能有返回值
class People:
    country='China'
    x=1

    def __init__(obj, name, age, sex): #obj=obj1,x='egon',y=18,z='male'
        # if type(name) is not str:
        #     raise TypeError('名字必须是字符串类型')
        obj.name = name
        obj.age = age
        obj.sex = sex


    def run(self):
        print('----->', self)


# obj1=People('egon',18,'male')
obj1=People(3537,18,'male')

# print(obj1.run)
# obj1.run() #People.run(obj1)
# print(People.run)

!!!__init__方法之为对象定制自己独有的特征
View Code

属性查找

类有两种属性:数据属性和函数属性

  1类的数据属性是所有对象共享的

  2类的函数属性是绑定给对象用的

对象的使用

school='xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx'
class OldboyStudent:
    school='oldboy'

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

    #self=stu1
    def learn(self):
        print('%s is learning' %self.name)


    # def learn(self):  #类内自调用
    #     print('is learning')

    def choose(self,course):
        print('%s is choosing %s' %(self.name,course))


# 调用类-》 产生类的对象,该对象也可以称为类的一个实例化,调用类的过程也称为类的实例化
stu1=OldboyStudent('李三胖',18,'male') #OldboyStudent.__init__(stu1,'李三胖',18,'male')
                                        # 在init里面为对象添加属性 stu1.name=name
                                        #定制对象独有的特征 相同的特征放在类中
# print(OldboyStudent.__dict__)
# print(stu1.__dict__)  #{'name': '李三胖', 'age': 18, 'sex': 'male'}
# print(stu1.__dict__['name']) #李三胖
# print(stu1.name) #李三胖
#
stu2=OldboyStudent('王大炮',28,'male')
# print(stu2.__dict__)  #{'name': '王大炮', 'age': 28, 'sex': 'male'}

# 类内部定义的变量是给所有对象共享,所有对象指向的都是同一个内存地址
# print(id(stu1.school))
# print(id(stu2.school))
# print(id(OldboyStudent.school))

# 31234736
# 31234736
# 31234736
# 类内部定义的函数,类可以使用,但类来用的时候就是一个普通函数,普通函数有几个参数就传入几个参数
# print(OldboyStudent.learn)
# OldboyStudent.learn(123 )

# <function OldboyStudent.learn at 0x00000000021D97B8>
# is learning


# 类内部定义的函数,其实是给对象使用的,而且是绑定给对象用,绑定给不同的对象就是不同的绑定方法
# print(stu1.learn)
# print(stu2.learn)
# <bound method OldboyStudent.learn of <__main__.OldboyStudent object at 0x00000000021D2860>>
# <bound method OldboyStudent.learn of <__main__.OldboyStudent object at 0x00000000021D2898>>

# 绑定方法的特殊之处在于,谁来调用,就会将谁当做第一个参数自动传入
# stu1.learn()   #OldboyStudent.learn(stu1)
# stu2.learn()   #OldboyStudent.learn(stu2)
# 李三胖 is learning
# 王大炮 is learning

# stu1.choose('python')
# stu2.choose('linux')
# 李三胖 is choosing python
# 王大炮 is choosing linux


# print(id(stu2))
# print(type(stu2))
# print(stu2)
                    #类与类型是一个概念
# l1=[1,2,3]  #l1=list([1,2,3])
# print(type(l1))
# print(id(l1))
# print(l1)
# l1.append(4)
# print(l1)
# list.append(l1,4)
# print(l1)

# l2=['a','b','c']
# l2.append('d')
# print(l2)     #['a', 'b', 'c', 'd']
# list.append(l2,'d')
# print(l2)   #['a', 'b', 'c', 'd']

print(int)
print(str)
print(dict)
print(tuple)
print(set)
print(OldboyStudent)        #类与类型是一个概念
# <class 'int'>
# <class 'str'>
# <class 'dict'>
# <class 'tuple'>
# <class 'set'>
# <class '__main__.OldboyStudent'>
View Code

对象之间的交互

class Garen:        #定义英雄盖伦的类,不同的玩家可以用它实例出自己英雄;
    camp='Demacia'  #所有玩家的英雄(盖伦)的阵营都是Demacia;
    def __init__(self,nickname,aggressivity=58,life_value=455): #英雄的初始攻击力58...;
        self.nickname=nickname  #为自己的盖伦起个别名;
        self.aggressivity=aggressivity #英雄都有自己的攻击力;
        self.life_value=life_value #英雄都有自己的生命值;
    def attack(self,enemy):   #普通攻击技能,enemy是敌人;
        enemy.life_value-=self.aggressivity #根据自己的攻击力,攻击敌人就减掉敌人的生命值。
# class Foo:
#     n=0
#     def __init__(self):
#         Foo.n+=1
#
#
# obj1=Foo()
# obj2=Foo()
# obj3=Foo()
#
#统计每次调用foo被调用的次数(调用就是产生对象)每次调用都运行一遍init
    # init是对象独有的 self.n 是只能看每个对象独有的调用次数,别的对象看不到
    # 所以写成foo.n 类是共有的 统计foo被调用的次数

# print(obj1.n)
# print(obj2.n)
# print(obj3.n)

# class Bar:
#     n=111111
#     def __init__(self,x):
#         self.x=x
# obj=Bar(111)
# print(obj.__dict__)  #{'x': 111}
# print(obj.n)   #111111
#
# obj.y=2   #增值
# obj.n=3
# print(obj.__dict__)   #{'x': 111, 'y': 2, 'n': 3}
# print(obj.n)   #3
#
# obj.x=123   #改值
# del obj.x   #删值
# print(obj.x)


'''
现实中的对象:
    人1
        特征:
            名字='刘晴政'
            攻击力=60
            生命值=100
        技能:
            咬

    人2
        特征:
            名字='王苗璐'
            攻击力=50
            生命值=100
        技能:
            咬

现实中的人类
    相同的特征
    相同的技能
        咬
'''


'''
现实中的对象:
    狗1
        特征:
            名字='武培其'
            品种="京巴"
            攻击力=80
            生命值=50
        技能:
            咬

    人2
        特征:
            名字='李杰'
            品种="藏獒"
            攻击力=200
            生命值=200
        技能:
            咬

现实中的狗类
    相同的特征
    相同的技能
        咬
'''
class PeoPle:
    def __init__(self,name,aggressivity,lif_value):
        self.name=name
        self.aggressivity=aggressivity
        self.life_value=lif_value

        #
    def bite(self,enemy):
        enemy.life_value-=self.aggressivity
        print('''
        人[%s]咬了一口狗[%s]
        狗掉血[%s]
        狗还剩血量[%s]
        '''%(self.name,enemy.name,self.aggressivity,enemy.life_value))

class Dog:
    def __init__(self,name,dog_type,aggressivity,life_value):
        self.name=name
        self.dog_type=dog_type
        self.aggressivity=aggressivity
        self.life_value=life_value
    def bite(self,enemy):
        enemy.life_value-=self.aggressivity
        print('''
        [%s]狗[%s]咬了一口人[%s]
        人掉血[%s]
        人剩余血量[%s]
        '''%(self.dog_type,self.name,enemy.name,self.aggressivity,enemy.life_value)
              )
p1=PeoPle('刘清正',50,100)
d2=Dog('李杰','藏獒',200,200)

d2.bite(p1)
p1.bite(d2)

'''
        [藏獒]狗[李杰]咬了一口人[刘清正]
        人掉血[200]
        人剩余血量[-100]
        

        人[刘清正]咬了一口狗[李杰]
        狗掉血[50]
        狗还剩血量[150]
        
'''
小练习1 人狗大战
class Zombie:
    #外界输入的name为‘普通僵尸’这种僵尸品种格式
    def __init__(self,name):
        self.name=name
        self.HP=100
        #如果用户随便输入 打造的就是普通僵尸
        if name not in ['普通僵尸','路障僵尸','铁桶僵尸']:
            self.name='普通僵尸'
            self.__armor=['',0]
        elif name.startswith('路障'):
            self.__armor=['路障',5]  #防具名,#防御值
        else:
            self.__armor=['铁桶',15] #防具名,#防御值

    @property   #可以取值
    def armor_name(self):
        return self.__armor[0]    #防具名

    @armor_name.setter  #可以重新赋值
    def armor_name(self,name):

        #给道具的参数不对,就不做任何修改
        if name not in ['','路障','铁通']:
            return
        #无道具要处理为普通僵尸
        if name =='':
            name='普通'
            self.__armor=['',0]  #防具名,#防御值
        elif name=='路障':
            self.__armor=['路障',5]  #防具名,#防御值

        else:
            self.__armor=['铁桶',15] #防具名,#防御值
        # 僵尸状态更新后,僵尸名也要修改
        self.name=name+'僵尸'

    @armor_name.deleter
    def armor_name(self):
        del self.__armor    #删除防具内 :防具名,防御值

    @property
    def armor_cout(self):  #防御值 只可以取值
        return self.__armor[1]




#
class Peopel:
    def __init__(self,name):
        self.name=name

    def beat(self,zombie):
        low_PH=25 - zombie.armor_cout #25-防御力 实际损失血量
        while zombie.HP>0:
            import time
            time.sleep(1)
            zombie.HP -= low_PH #25-防御力
            print('''
            %s攻击了%s,僵尸损失了%s血,还剩%s
            '''%(self.name,zombie.name,low_PH,zombie.HP))
        print('%s 击杀了%s'%(self.name,zombie.name))


import random
class Game(Zombie):
    name='大战僵尸'
    @classmethod
    def start(cls):
        print(cls.name)
        for i in range(1,4):
            name=random.choice(['普通僵尸','路障僵尸','铁桶僵尸'])
            zombie=Zombie(name)
            print(zombie.name)
            # print('1:路障 2:铁通 0:不改')
            # choice = input('输入更名选项:')
            # while choice:
            #     if choice==1:
            #         name1='路障'
            #     elif choice==2:
            #         name1='铁桶'
            #     break
            # super().armor_name(name1)
            people = random.choice(['owen', 'egon', 'alex'])
            people=Peopel(people)
            print('开始击杀第%d只僵尸'%i)
            people.beat(zombie)
            print('第 %s 只僵尸已被击杀完毕'%i)


Game.start()
大战僵尸

属性方法的封装

# class Student:
#     pass
# stu=Student()
#
# def func(arg):
#     print('func run')
# Student.func=func
# stu.func()    #func run 调用的是类中的

# 总结:对象调用类的方法:
# class A:
#     def test(self):
#         print(self)
#         pass
#
# a=A()
# a.test()
# A.test(a)
# A.__dict__['test'](a)

# class Tool:
    #类方法:可以被类与对象调用的方法,类调用第一个参数一定要传(不加clssmethod)
    #类方法不建议拿对象调用 (加classmethod)就是类的方法了
    # @classmethod  #类方法:列调用的时候不需要传第一个参数
    # def add(cls,n1,n2): #如果把cls 删掉默认会把下一个参数当成 接收类本身的参数(类调用时不传类名了)
        # 但是上面加了classmethod之后再调用会默认把列自动传入 会报错
        # print(id(n1))   #8791421609072
        # cls.test()
        # return n1+n2

    # @classmethod
    # def test(cls):
    #     pass
# print(Tool.add(10,20))
# tool=Tool
# print(tool.add(100,200))
# print(id(Tool),id(tool))  #5392200 5392200

# 对象调用所属类的类方法,默认第一个参数传入的是 对象.__class__ 就是所属类
# print(tool.__class__)

class OldBoy:
    #属于类的属性
    name='老男孩'

    #属于对象的属性
    def __init__(self,name):
        self.name=name

    #属于类的方法
    #需求:获取机构的名字
    @classmethod
    def get_class_name(cls):
        return cls.name

    #对象的方法
    #需求:获取校区的名字
    def get_school_name(self):
        return self.name

#先创建校区
shanghai=OldBoy('上海校区')
shenzhen=OldBoy('深圳校区')

# 类方法的使用
# 建议使用列调用
# print(OldBoy.get_class_name())
#类方法拿对象调用并没有什么新增的意义,不建议拿对象调用
print(shanghai.get_class_name())
print(shenzhen.get_class_name())
# 老男孩
# 老男孩

# 对象方法的使用
# 类调用对象方法,必须把要操作的对象手动传入,不建议使用
# print(OldBoy.get_school_name(shanghai))   #上海校区
# print(OldBoy.get_school_name(shenzhen))   #深圳校区

# 对象调用对象方法,默认将自身传入,建议使用
# print(shanghai.get_school_name())
# print(shenzhen.get_school_name())
# 上海校区
# 深圳校区

# n1=OldBoy.get_class_name(123)
# print(n1)   多给一个参数,调用类对象,会自动传类本身

# shanghai=OldBoy('上海校区')  #对象的属性
# n2=shanghai.get_class_name()
# print(n2)  #老男孩

# class A:
#     x=10
#     y=20
#     def f1(self):
#         print('f1 run')
#     def f2(self):
#         print('f2 run')
#
#     #找到保险箱
#     def get_box(self):
#         print('找到保险箱')
#         self.get_money()
#
#     #保险箱取钱操作
#     def get_money(self):
#         print('输入密码,取出100零花钱')
#
# a=A()
# print(a.x) #调用类的属性(也就是对象公有属性)
# print(a.y) # #调用类的属性(也就是对象公有属性)
# a.f1()      #调用对象方法(调用类的技能)
# a.f2()      # 调用对象方法(调用类的技能)
#
# a.get_box()
# # 找到保险箱
# # 输入密码,取出100零花钱
# a.get_money()
# 输入密码,取出100零花钱(没有封装)可以直接访问

# 将类中的一些功能与属性,进行隐藏,不让外界直接访问(间接访问)

#封装:对外隐藏列中一些属性与方法的实现细节
#优点: 外界不能直接访问,让内部的属性与方法具有安全保障

# class A:
#     # __开头的属性,在外界不能通过 cord | __cord 直接访问:对外隐藏了
#     __cord='020334'
#
#     # __开头的方法,在外界不能通过 get_money | __get_money 直接访问:对外隐藏了
#     @classmethod
#     def __get_money(cls):
#         print('输入密码,取出100零花钱')
#
#     # 内部还是可以直接访问__开头的属性与方法
#     @classmethod
#     def test(cls,flag):
#         print('tset方法被外界调用')
#         # 在调用test与访问具体数据与功能间添加安全处理的操作
#         if flag=='自家人':
#             print(cls.__cord)
#             cls.__get_money()

# print(a.__cord)
# A.__get_money()
# A.test('自家人')  #类的自调用

# tset方法被外界调用
# 020334
# 输入密码,取出100零花钱

# 封装的原理:把__开头的名字更名为_类名__变量名(属性|方法),所以直接通过类名.__变量名就访问不到
# print(A.__dict__)
# {'__module__': '__main__', '_A__cord': '020334', '_A__get_money': <classmethod object at 0x0000000001DD90B8>, 'test': <classmethod object at 0x0000000001DD9128>, '__dict__': <attribute '__dict__' of 'A' objects>, '__weakref__': <attribute '__weakref__' of 'A' objects>, '__doc__': None}
# print(A._A__cord)
# A._A__get_money()
# 020334
# 输入密码,取出100零花钱
View Code

 

转载于:https://www.cnblogs.com/lakei/p/10738732.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值