zoukankan      html  css  js  c++  java
  • 类的相关内置函数及反射

    类变量的内存位置相关练习

    1.1

    class StarkConfig(object):
        list_display = []
    
        def get_list_display(self):
            self.list_display.insert(0,33)
            return self.list_display
    
    class RoleConfig(StarkConfig):
        list_display = [11,22]
    
    
    s1 = StarkConfig()
    result1 = s1.get_list_display()
    print(result1) # 33
    result2 = s1.get_list_display()
    print(result2) # 33 33
    练习1

    1.2

    class StarkConfig(object):
        list_display = []
    
        def get_list_display(self):
            self.list_display.insert(0,33)
            return self.list_display
    
    class RoleConfig(StarkConfig):
        list_display = [11,22]
    
    
    s1 = StarkConfig()
    s2 = StarkConfig()
    
    result1 = s1.get_list_display()
    print(result1)  # [33]
    
    result2 = s2.get_list_display()
    print(result2) # [33,33]
    练习2

    1.3

    class StarkConfig(object):
        list_display = []
    
        def get_list_display(self):
            self.list_display.insert(0,33)
            return self.list_display
    
    class RoleConfig(StarkConfig):
        list_display = [11,22]
    
    
    s1 = StarkConfig()
    s2 = RoleConfig()
    
    result1 = s1.get_list_display()
    print(result1)           # [33]
    
    result2 = s2.get_list_display()
    print(result2)            # [33,11,22]
    练习3

    类的相关内置函数

     1.1 issubclass(参数1,参数2)

    检查第一个参数是否是第二个参数的子类及子类的子类(比较圆滑,只要是长辈都返回True),返回True和Flase,可以判断对象是不是由某一个指定类或其父类

    class Base(object):
        pass
    
    
    class Foo(Base):
        pass
    
    
    class Bar(Foo):
        pass
    
    
    print(issubclass(Foo, Base))
    print(issubclass(Foo, object))
    print(issubclass(Bar, Foo))
    print(issubclass(Bar, Base))
    print(issubclass(Bar, object))
    
    # 输出结果:
    True
    True
    True
    True
    True
    View Code

    1.2 type

    获取当前对象是由哪个类创建,只承认当前对象的直接上级(比较死板),可以判断对象是不是由某一个指定类创建

    class Foo(object):
        pass
    
    obj = Foo()
    
    print(obj,type(obj)) # 获取当前对象是由那个类创建。
    
    # 输出结果:
    <__main__.Foo object at 0x00000272D5EB6320> <class '__main__.Foo'>
    
    # 可以人为判断
    
    if type(obj) == Foo:
        print('obj是Foo类型')
    
    # 因判断为True
    # 输出结果:
    obj是Foo类型
    View Code

    1.3 isinstance(对象,类)

    检查第一个参数(对象)是否是第二个参数(类及父类)的实例,返回True和Flase

    class Base(object):
        pass
    
    class Foo(Base):
        pass
    
    obj1 = Foo()
    
    print(isinstance(obj1,Foo)) # True
    print(isinstance(obj1,Base)) #True     由此可见是其父类也返回True
    
    obj2 = Base()
    print(isinstance(obj2,Foo))  #Flase      由此可见,是其子类不可以,返回Flase
    View Code

    用科学的方法判断是函数还是方法

    我们一般认为,写在类中的就可以叫做方法,写在外面的就可以叫做函数

    科学的方法判断就是判断它是不是方法类或函数类中的,因为在python中,一切皆对象,方法和函数也是某个类的对象

    MethodType(方法),FunctionType(函数)

    from types import MethodType,FunctionType
    def check(arg):
        """
        检查arg是方法还是函数?
        :param arg:
        :return:
        """
        if isinstance(arg,MethodType): # 如果arg是MethodType类的实例
    
            print('arg是一个方法')
        elif isinstance(arg,FunctionType): # 如果arg是FunctionType类的实例
            print('arg是一个函数')
        else:
            print('不知道是什么')
    
    def func():
        pass
    
    class Foo(object):
        def detail(self): # 默认传入self参数
            pass
        @staticmethod
        def xxx(): # 没有默认参数
            pass
    
    
    check(func) #这是一个函数
    obj = Foo()
    check(obj.detail) # 这是一个方法
    check(obj.xxx)  # 这是一个函数
    
    """
    由上述可知,判断是方法还是函数,也看有没有其怎么调用或是否有默认self参数传入
    """
    View Code

    小结:

    对象.xxx --> xxx就是方法

    类.xxx --> xxx就是函数

    xxx --> xxx就是函数

    反射

    geattr(对象,字符串)

    根据字符串为参数,去对象中寻找与之同名的成员

    去模块中寻找

    """
    建立一个handler.py文件
    
    """
    f0 = 9
    
    def f1():
        print('F1')
    
    def f2():
        print('F2')
    
    def f3():
        print('F3')
    
    def f4():
        print('F4')
    
    def f5():
        print('F5')
    
    """
    同目录级引入上述handler模块
    
    """
    
    import handler
    
    while True:
        print("""
        系统支持的函数有:
            1. f1
            2. f2
            3. f3
            4. f4
            5. f5
        """)
        val = input("请输入要执行的函数:") # val = "f1"
    
        if hasattr(handler,val):
            func_or_val = getattr(handler,val)     # 根据字符串为参数,去模块中寻找与之同名的成员。
            if isinstance(func_or_val,FunctionType):
                func_or_val()
            else:
                print(func_or_val)
        else:
            print('handler中不存在输入的属性名')
    View Code

    面向对象中用geattr

     1 class Foo(object):
     2 
     3     country = "中国"
     4 
     5     def func(self):
     6        pass
     7 
     8 v = getattr(Foo,'func') # Foo.func # 根据字符串为参数,去类中寻找与之同名的成员。
     9 print(v) # 输出fun的内存地址,通过类查找,此时 func是个函数
    10 
    11 obj = Foo()
    12 v = getattr(obj,"func") # obj.func # 根据字符串为参数,去对象中寻找与之同名的成员。
    13 print(v)  # 输出func的内存地址,通过对象查找,此时func是个方法
    反射简单示例

    hasattr

    根据字符串的形式,去判断对象中是否有成员。

    import xx
    
    v3 = hasattr(xx,'x1')
    v4 = hasattr(xx,'f1')
    v4 = hasattr(xx,'f1')
    v5 = hasattr(xx,'xxxxxxx')
    print(v3,v4,v5)
     # True True False
    View Code

    setattr

    根据字符串的形式,去判断对象中动态的设置一个成员(在内存中)

    class Foo(object):
    
        def __init__(self,a1):
            self.a1 = a1
            self.a2 = None
    
    obj = Foo(1)
    
    
    v1 = getattr(obj,'a1')
    print(v1) # 1
    
    setattr(obj,'a2',2)    # 若__init__没有a2参数,不建议这么写,因为没有人知道你其中还有其    
                                  # 他参数   若想写,最好在__init__那添加 a2 = None
    v2 = getattr(obj,'a2')
    print(v2)  # 2                                    
    View Code

    delattr

    根据字符串的形式,去判断对象中动态的设置一个成员(内存中)

    import xx
    
    delattr(xx,'x1')
    v9 = getattr(xx,'x1')
    print(v9)
    # 因删除了 x1 所以会报错
    
    # AttributeError: module 'xx' has no attribute 'x1'
    View Code

    getattr的实际应用

    class Account(object):
        func_list = ['login', 'logout', 'register']
    
        def login(self):
            """
            登录
            :return:
            """
            print('登录111')
    
        def logout(self):
            """
            注销
            :return:
            """
            print('注销111')
    
        def register(self):
            """
            注册
            :return:
            """
            print('注册111')
    
        def run(self):
            """
            主代码
            :return:
            """
            print("""
                请输入要执行的功能:
                    1. 登录
                    2. 注销
                    3. 注册
            """)
    
            choice = int(input('请输入要执行的序号:'))
            func_name = Account.func_list[choice-1]
    
            # func = getattr(Account,func_name) # Account.login
            # func(self)
    
            func = getattr(self, func_name)  # self.login
            func()
    
    obj1 = Account()
    obj1.run()
    
    obj2 = Account()
    obj2.run()
    练习
    
    
  • 相关阅读:
    VMware workstation安装Windows Server 2012 R2步骤详解(附下载链接)
    英文系统下Oracle SQL Developer 汉化
    C# .NET Core Linux、Windows统一文件路径解决方法
    C# DataTable 转JSON、List 转DataTable、DataTable转List
    IIS无法启动计算机上"."的服务W3SVC(World Wide Web 发布服务)正在停止
    SQLServer 数据库变成单个用户后无法访问的解决方法
    C# webform中无法获取修改后的textbox值
    SqlServer try catch 捕获触发器存储过程异常,结合 transaction 事务
    DataTable.Select筛选过滤数据返回DataRow[]转为DataTable添加到DataSet
    easyui datagrid checkbox复选框取消单击选中事件、初始全选全不选等问题解决
  • 原文地址:https://www.cnblogs.com/--kai/p/9562464.html
Copyright © 2011-2022 走看看