zoukankan      html  css  js  c++  java
  • python 要掌握面向对象,你得会做这些题

    1,面向对象三大特性,各有什么用处,说说你的理解。

    继承:解决代码重用问题
    
    多态:多态性,可以在不考虑对象类型的情况下而直接使用对象
    
    封装:明确的区分内外,控制外部对隐藏属性的操作行为,隔离复杂度
    

      

    2,类的属性和对象的属性有什么区别?

    类的属性:数据属性和函数属性,数据属性是所有对象共有的,函数属性是绑定对象使用的
    
    对象的属性:对象是类的实例化
    

      

    3,面向过程编程与面向对象编程的区别与应用场景?

    面向过程:复杂的问题流程化,简单化
    应用场景:不再需要扩展了,监测脚本,自动部署脚本,软件解压安装
    
    面向对象:特征与技能的结合体 一切皆对象
    应用场景:用户需求经常变化,互联网应用,游戏,企业内部应用
    

      

    4,类和对象在内存中是如何保存的。

    类和对象的属性:以字典的形式保存的
    

      

    5,什么是绑定到对象的方法、绑定到类的方法、解除绑定的函数、如何定义,如何调用,给谁用?有什么特性

    绑定到对象的方法:就应该由对象来调用,def tell_info(self):...obj.tell_info()
    
    绑定到类的方法:就应该由类来调用,@classmethod def from_conf(cls):... class.from_conf()
    
    非绑定方法:不与类或对象绑定,谁都可以调用,@staticmethod def create_id():...
                    obj.create_if()/class.create_id()
    

      

    6,使用实例进行 获取、设置、删除 数据, 分别会触发类的什么私有方法

     class A(object):
         pass
    
     a = A()
    
     a["key"] = "val"
     a = a["key"]
     del a["key"]
    
    # class A(object):
    #     def __setitem__(self, key, value):
    #         self.__dict__[key] = value
    #
    #     def __getitem__(self, item):
    #         # return self.__dict__[item]
    #         return self.__dict__.get(item)
    #
    #     def __delitem__(self, key):
    #         del self.__dict__[key]
    #
    # a = A()
    # a["key"] = "val"
    # print(a.__dict__)
    # # a = a["key"]
    # # print(a)
    # del a["key"]
    # print(a.__dict__)
    

      

    7,python中经典类和新式类的区别

    经典类:py2 没有继承object的类,以及它的子类都称之为经典类  --> 深度优先
    
    新式类:py3 继承object的类,以及它的子类都称之为新式类       -->广度优先
    

      

    8,如下示例, 请用面向对象的形式优化以下代码

    1、在没有学习类这个概念时,数据与功能是分离的
       def exc1(host,port,db,charset):
         conn=connect(host,port,db,charset)
         conn.execute(sql)
         return xxx
       def exc2(host,port,db,charset,proc_name)
         conn=connect(host,port,db,charset)
         conn.call_proc(sql)
         return xxx
       # 每次调用都需要重复传入一堆参数
       exc1('127.0.0.1',3306,'db1','utf8','select * from tb1;')
       exc2('127.0.0.1',3306,'db1','utf8','存储过程的名字')
    

      

    9,示例1, 现有如下代码, 会输出什么:

     class People(object):
          __name = "luffy"
          __age = 18
    
      p1 = People()
      print(p1.__name, p1.__age)
    

      

    class People(object):
        __name = "luffy"
        __age = 18
    
    
    p1 = People()
    
    # print(p1.__name, p1.__age)
    # 报错:AttributeError: 'People' object has no attribute '__name'
    
    print(p1.__dict__)          #{}
    print(People.__dict__)
    # {'__module__': '__main__', '_People__name': 'luffy', 
    # '_People__age': 18, '__dict__': <attribute '__dict__' of 'People' objects>, 
    # '__weakref__': <attribute '__weakref__' of 'People' objects>, '__doc__': None}
    print(p1._People__name,p1._People__age)  # luffy 18
    

      

    10,示例2, 现有如下代码, 会输出什么:

    class People(object):
    
       def __init__(self):
           print("__init__")
    
       def __new__(cls, *args, **kwargs):
           print("__new__")
           return object.__new__(cls, *args, **kwargs)
    
    People()
    

      

    # 结果:__new__
    # __init__
    

      

    11,请简单解释Python中 staticmethod(静态方法)和 classmethod(类方法), 并分别补充代码执行下列方法。

      静态方法:非绑定方法,类和对象都可以调用

      类方法:绑定给类的方法啊,类调用

    class A(object):
    
       def foo(self, x):
           print("executing foo(%s, %s)" % (self,x))
    
       @classmethod
       def class_foo(cls, x):
           print("executing class_foo(%s, %s)" % (cls,x))
    
       @staticmethod
       def static_foo(x):
           print("executing static_foo(%s)" % (x))
    
    a = A()
    
    class A(object):
        def __init__(self,name):
            self.name=name
    
        def foo(self, x):
            print("executing foo(%s, %s)" % (self,x))
    
        @classmethod
        def class_foo(cls, x):
            print("executing class_foo(%s, %s)" % (cls,x))
    
        @staticmethod
        def static_foo(x):
            print("executing static_foo(%s)" % (x))
    
    # a = A('alice')
    # a.foo('alice')
    # A.class_foo('alice')
    # a.static_foo('alice')
    # A.static_foo('alice')
    '''
    executing foo(<__main__.A object at 0x000002A5FED12AC8>, alice)
    executing class_foo(<class '__main__.A'>, alice)
    executing static_foo(alice)
    executing static_foo(alice)
    '''
    

      

      

    12,请执行以下代码,解释错误原因,并修正错误。

      错误原因:@property可以将函数属性转化为数据属性

    class Dog(object):
    
       def __init__(self,name):
           self.name = name
    
       @property
       def eat(self):
           print(" %s is eating" %self.name)
    
    d = Dog("ChenRonghua")
    d.eat()
    

     报错内容:

    Traceback (most recent call last):
      File "D:/py.py", line 27, in <module>
        d.eat()
    TypeError: 'NoneType' object is not callable
    

    改正如下:

    class Dog(object):
    
       def __init__(self,name):
           self.name = name
    
       @property
       def eat(self):
           print(" %s is eating" %self.name)
    
    d = Dog("ChenRonghua")
    d.eat
    

      因为有了property,用户就可以直接输入得到结果,对于使用者来说,感知不到其属性,这就是使用property的方便之处,此方法必须有一个返回值。return 或者print都可以。

    为什么要用property?

       一个类的函数定义成特性以后,对象再去使用的时候obj.name,根本无法察觉自己的name是执行了一个函数然后计算出来的,这种特性的使用方式遵循了统一访问的原则

    13,下面这段代码的输出结果将是什么?请解释。

    class Parent(object):
       x = 1
    
    class Child1(Parent):
       pass
    
    class Child2(Parent):
       pass
    
    print(Parent.x, Child1.x, Child2.x)
    Child1.x = 2
    print(Parent.x, Child1.x, Child2.x)
    Parent.x = 3
    print(Parent.x, Child1.x, Child2.x)
    
    # 1 1 1 继承自父类的类属性x,所以都一样,指向同一块内存地址
    # 1 2 1 更改Child1,Child1的x指向了新的内存地址
    # 3 2 3 更改Parent,Parent的x指向了新的内存地址
    

      

    14,多重继承的执行顺序,请解答以下输出结果是什么?并解释。

     super()表示的是 子类的mro()列表中的下一个
        print(G.mro())
            [<class '__main__.G'>, <class '__main__.D'>, <class '__main__.A'>, <class '__main__.B'>, <class 'object'>]
        print(F.mro())
            [<class '__main__.F'>, <class '__main__.C'>, <class '__main__.B'>, <class '__main__.D'>, <class '__main__.A'>, <class 'object'>]
    

      

    class A(object):
       def __init__(self):
           print('A')
           super(A, self).__init__()
    
    class B(object):
       def __init__(self):
           print('B')
           super(B, self).__init__()
    
    class C(A):
       def __init__(self):
           print('C')
           super(C, self).__init__()
    
    class D(A):
       def __init__(self):
           print('D')
           super(D, self).__init__()
    
    class E(B, C):
       def __init__(self):
           print('E')
           super(E, self).__init__()
    
    class F(C, B, D):
       def __init__(self):
           print('F')
           super(F, self).__init__()
    
    class G(D, B):
       def __init__(self):
           print('G')
           super(G, self).__init__()
    
    if __name__ == '__main__':
       g = G()
       f = F()
    
    # G
    # D
    # A
    # B
    #
    # F
    # C
    # B
    # D
    # A
    

      

    15,请编写一段符合多态特性的代码.

    class Animal:
        def __init__(self, name):
            self.name = name
    
    
    class People(Animal):
        def talk(self):
            print('%s is talking' % self.name)
    
    
    class Dog(Animal):
        def talk(self):
            print('%s is talking' % self.name)
    
    
    def func(animal):
        animal.talk()
    
    # p=People('alice')
    # d=Dog('wang')
    # func(p)
    # func(d)
    '''
    alice is talking
    wang is talking
    '''
    

      

    16,很多同学都是学会了面向对象的语法,却依然写不出面向对象的程序,原因是什么呢?原因就是因为你还没掌握一门面向对象设计利器,即领域建模,请解释下什么是领域建模,以及如何通过其设计面向对象的程序?http://www.cnblogs.com/alex3714/articles/5188179.html 此blog最后面有详解

    领域模型,顾名思义,就是需求所涉及的领域的一个建模,更通俗的讲法是业务模型。
        定义:
            需求到面向对象的桥梁
        作用:
            1.发掘重要的业务领域概念
            2.建立业务领域概念之间的关系 
        方法:
            从用例中找名词
        领域建模的三字经方法:找名词、加属性、连关系。
            参考:http://www.cnblogs.com/linhaifeng/articles/6182264.html#_label15 
                 http://www.cnblogs.com/linhaifeng/articles/7341318.html
    

      

    17,请写一个小游戏,人狗大站,2个角色,人和狗,游戏开始后,生成2个人,3条狗,互相混战,人被狗咬了会掉血,狗被人打了也掉血,狗和人的攻击力,具备的功能都不一样。注意,请按题14领域建模的方式来设计类。

    class Animal:
        def __init__(self, name,life_value,aggressivity):
            self.name = name
            self.life_value = life_value
            self.aggressivity = aggressivity
    
        def attack(self,enemy):
            enemy.life_value -= self.aggressivity
    
    
    class People(Animal):
        camp='home'
        def attack(self,enemy):
            super().attack(enemy)
            print('from people')
    
    class Dog(Animal):
        camp='wo'
        def attack(self,enemy):
            super().attack(enemy)
            print('from dog')
    
    p1=People('alice',80,30)
    p1=People('alex',80,30)
    d1=Dog('w1',90,50)
    d2=Dog('w2',90,50)
    d3=Dog('w3',90,50)
    
    # print(p1.life_value)
    # d1.attack(p1)
    # print(p1.life_value)
    
    # print(d1.life_value)
    # p1.attack(d1)
    # print(d1.life_value)
    

      

    18,编写程序, 在元类中控制把自定义类的数据属性都变成大写.

     

    class Mymetaclass(type):
        def __new__(cls,name,bases,attrs):
            update_attrs={}
            for k,v in attrs.items():
                if not callable(v) and not k.startswith('__'):
                    update_attrs[k.upper()]=v
                else:
                    update_attrs[k]=v
            return type.__new__(cls,name,bases,update_attrs)
     
    class Chinese(metaclass=Mymetaclass):
        country='China'
        tag='Legend of the Dragon' #龙的传人
        def walk(self):
            print('%s is walking' %self.name)
     
     
    print(Chinese.__dict__)
    '''
    {'__module__': '__main__',
     'COUNTRY': 'China', 
     'TAG': 'Legend of the Dragon',
     'walk': <function Chinese.walk at 0x0000000001E7B950>,
     '__dict__': <attribute '__dict__' of 'Chinese' objects>,                                         
     '__weakref__': <attribute '__weakref__' of 'Chinese' objects>,
     '__doc__': None}
    '''
    

      

    19,编写程序, 在元类中控制自定义的类无需init方法.

    class Mymeta(type):
        def __new__(cls,class_name,class_bases,class_dic):
            update_dic = {}
            for i in class_dic:
                if not callable(class_dic[i]) and not i.startswith('__'):
                    update_dic[i.upper()]=class_dic[i]
                else:
                    update_dic[i]=class_dic[i]
            return type.__new__(cls,class_name,class_bases,update_dic)
    
        def __call__(self, *args, **kwargs):
            obj=object.__new__(self)
            if args:
                raise TypeError('must be keyword argument')
            for i in kwargs:
                obj.__dict__[i]=kwargs[i]
            return obj
    
    class Chinese(metaclass=Mymeta):
        country='china'
        tag='legend of the dragon'
    
        def talk(self):
            print('%s is talking'%self.name)
    
    # print(Chinese.__dict__)
    # ch=Chinese(name='alice',age=18)
    # ch.talk()
    # print(ch.__dict__)
    

      

    20,编写程序, 编写一个学生类, 要求有一个计数器的属性, 统计总共实例化了多少个学生.

    class Student:
        __count = 0
        def __init__(self, name, age):
            self.name = name
            self.age = age
            Student.__count += 1
    
        @property
        def talk(self):
            print('%s is talking' % self.name)
    
        @staticmethod
        def tell_count():
            print('总共实例化了 %s 人' % Student.__count)
    
    # s1 = Student('alice', 18)
    # s2 = Student('alex', 20)
    # s3 = Student('egon', 28)
    # Student.tell_count()
    # s1.tell_count()
    # s1.talk
    # s2.talk
    

     结果:

    # 结果:
    # 1
    # {'name': 'james', 'sex': 'male', 'age': 32}
    # 2
    # {'name': 'enbede', 'sex': 'male', 'age': 23}
    # 2
    # {'__module__': '__main__', '_count': 2, '__init__': <function Student.__init__ at 0x00000190B1B959D8>, 'learn': <property object at 0x00000190B19047C8>, 'tell_count': <staticmethod object at 0x00000190B1B9CAC8>, '__dict__': <attribute '__dict__' of 'Student' objects>, '__weakref__': <attribute '__weakref__' of 'Student' objects>, '__doc__': None}
    # 总共实例化了:2
    # james is learning
    

      

    # _*_ coding: utf-8 _*_
    '''
    练习1:编写一个学生类,产生一堆学生对象, (5分钟)
    要求:
    有一个计数器(属性),统计总共实例了多少个对象
    '''
    class Student:
        count = 0
        def __init__(self,name,sex,age):
            self.name = name
            self.sex = sex
            self.age = age
            Student.count +=1
    
        def learn(self):
            print("%s is learning"%self.name)
    
    stu1 = Student('james','male',32)
    print(stu1.count)
    print(stu1.__dict__)
    stu2 = Student('enbede','male',23)
    print(stu2.count)
    print(stu2.__dict__)
    print(Student.count)
    print(Student.__dict__)
    # 结果:
    # 1
    # {'name': 'james', 'sex': 'male', 'age': 32}
    # 2
    # {'name': 'enbede', 'sex': 'male', 'age': 23}
    # 2
    # {'__module__': '__main__', 'count': 2, '__init__': <function Student.__init__ at 0x000001E5DA9759D8>, 'learn': <function Student.learn at 0x000001E5DA975A60>, '__dict__': <attribute '__dict__' of 'Student' objects>, '__weakref__': <attribute '__weakref__' of 'Student' objects>, '__doc__': None}
    # 
    # Process finished with exit code 0
    

      

    21,编写程序, A 继承了 B, 俩个类都实现了 handle 方法, 在 A 中的 handle 方法中调用 B 的 handle 方法

    class B:
        def handle(self):
            print('from B handle')
    
    class A(B):
        def handle(self):
            super().handle()
            # print('from A handle')
    # a=A()
    # a.handle()
    

      

    22,编写程序, 如下有三点要求:

    1. 自定义用户信息数据结构, 写入文件, 然后读取出内容, 利用json模块进行数据的序列化和反序列化
    2. 定义用户类,定义方法db,例如 执行obj.db可以拿到用户数据结构
    3. 在该类中实现登录、退出方法, 登录成功将状态(status)修改为True, 退出将状态修改为False(退出要判断是否处于登录状态).密码输入错误三次将设置锁定时间(下次登录如果和当前时间比较大于10秒即不允许登录)
    import json
    import time
    class User:
        def __init__(self, name, password):
            self.name = name
            self.password = password
            self.status = False
            self.timeout = 0
    
        @property
        def db(self):
            with open(self.name+'.txt', 'r', encoding='utf-8') as f:
                data = json.load(f)
            return data
    
        def save(self):
            obj={}
            obj[self.name]={'password':self.password,'status':self.status,'timeout':self.timeout}
            with open(self.name+'.txt', 'w', encoding='utf-8') as f:
                json.dump(obj,f)
    
        def login(self):
            with open(self.name+'.txt', 'r+', encoding='utf-8') as f:
                data = json.load(f)
                count = 0
                while count < 3:
                    password = input('password>>:').strip()
                    if password != data[self.name]['password']:
                        count += 1
                        continue
                    else:
                        if data[self.name]['timeout'] != 0:
                            if time.time() - data[self.name]['timeout'] > 10:
                                print('不允许登录了!超时')
                                break
                            else:
                                data[self.name]['status'] = True
                                f.seek(0)
                                f.truncate()
                                json.dump(data, f)
                                print('----welcome----')
                                break
                        else:
                            data[self.name]['status'] = True
                            f.seek(0)
                            f.truncate()
                            json.dump(data, f)
                            print('----welcome----')
                            break
    
                else:
                    data[self.name]['timeout']=time.time()
                    f.seek(0)
                    f.truncate()
                    json.dump(data,f)
    
    
        def quit(self):
            with open(self.name+'.txt', 'r+', encoding='utf-8') as f:
                data = json.load(f)
                if data[self.name]['status'] == True:
                    data[self.name]['status'] = False
                    f.seek(0)
                    f.truncate()
                    json.dump(data, f)
                else:
                    print('您是退出状态!')
    
    
    # alex=User('alex','123')
    # egon=User('egon','456')
    # # alex.save()
    # # egon.save()
    # # print(alex.db)
    # # print(egon.db)
    # # alex.login()
    # alex.quit()
    # # egon.quit()
    # print(alex.db)
    # print(egon.db)
    
    # alex.login()
    # egon.login()
    

      

    23,用面向对象的形式编写一个老师角色, 并实现以下功能, 获取老师列表, 创建老师、删除老师、创建成功之后通过 pickle 序列化保存到文件里,并在下一次重启程序时能读取到创建的老师, 例如程序目录结构如下.

    .
    |-- bin/
    |   |-- main.py         程序运行主体程序(可进行菜单选择等)
    |-- config/
    |   |-- settings.py     程序配置(例如: 配置存储创建老师的路径相关等)
    |-- db                  数据存储(持久化, 使得每次再重启程序时, 相关数据对应保留)
    |   |-- teachers/          存储所有老师的文件
    |   |-- ...                ...
    |-- src/                程序主体模块存放
    |   |-- __init__.py
    |   |-- teacher.py      例如: 实现老师相关功能的文件
    |   |-- group.py        例如: 实现班级相关的功能的文件
    |-- manage.py           程序启动文件
    |-- README.md           程序说明文件
    

      

    24,根据23 题, 再编写一个班级类, 实现以下功能, 创建班级, 删除班级, 获取班级列表、创建成功之后通过 pickle 序列化保存到文件里,并在下一次重启程序时能读取到创建的班级.

     

    25,根据 23题, 编写课程类, 实现以下功能, 创建课程(创建要求如上), 删除课程, 获取课程列表

     

    26,根据23 题, 编写学校类, 实现以下功能, 创建学校, 删除学校, 获取学校列表

     

    27,通过23题, 它们雷同的功能, 是否可以通过继承的方式进行一些优化

    伪代码
    class Behavior(object):
    
        def fetch(self, keyword):
            通过 keyword 参数 查询出对应的数据列表
    
    class School(Behavior):
    
        pass
    
    class Teacher(Behavior):
    
        pass
    
    s = School()
    t = Teacher()
    
    s.fetch("school")
    t.fetch("teacher")
    

      

    28:编写一个学生类,产生一堆学生对象

      要求:有一个计数器(属性),统计总共实例了多少个对象

    class Studentclass:
        school = 'jiaotong university'
        count = 0
    
        def __init__(self,name,age,sex):
            self.name = name
            self.age = age
            self.sex =sex
            Studentclass.count +=1
        def learn(self):
            print('%s is learning'%self.name)
    stu1 = Studentclass('james',23,'male')
    stu2 = Studentclass('poal',24,'male')
    stu3 = Studentclass('harden',25,'male')
    print(Studentclass.count)
    print(stu1.__dict__)
    print(stu2.__dict__)
    print(stu3.__dict__)
    print(stu1.count)
    print(stu2.count)
    print(stu3.count)
    

      

    29:模仿王者荣耀定义两个英雄类

      要求:

    1. 英雄需要有昵称、攻击力、生命值等属性;
    2. 实例化出两个英雄对象;
    3. 英雄之间可以互殴,被殴打的一方掉血,血量小于0则判定为死亡。
    class Hero:
        def __init__(self,nickname,life_value,aggresivity):
            self.nickname = nickname
            self.life_value = life_value
            self.aggresivity = aggresivity
        def attack(self,enemy):
            enemy.life_value -= self.aggresivity
    
    class Garen(Hero):
       pass
    
    class Riven(Hero):
        pass
    g1=Garen('草丛论',100,20)
    r1 = Riven('放逐之刃',80,50)
    
    print(r1.life_value)
    g1.attack(r1)
    print(r1.life_value)
    

      

  • 相关阅读:
    平台调用中的数据封送处理
    JavaScript 中的事件流
    Jquery插件 表格固定表头
    ASP.NET MVC Action Filter与内置的Filter实现
    getCurrentScript的改进
    analyze spring framework source
    Windows Azure: Service Bus Brokered Messaging DeadLetterQueue 使用详解
    C#截图
    权限系统
    音乐播放器
  • 原文地址:https://www.cnblogs.com/wj-1314/p/8734839.html
Copyright © 2011-2022 走看看