zoukankan      html  css  js  c++  java
  • 使用type在对象方法中调用类方法

    type简介

    type在Python中的作用是创建一个类。

    我们创建类的时候一般会使用这样的方法:

    # -*- coding:utf-8 -*-
    
    class Student(object):
    
        country = "China"
    
        def add(self,x:int,y:int)->int:
            return x+y
    
    s1 = Student()
    print(s1.country)
    print(s1.add(12,23))

    当然也可以使用type方法创建类,效果与上面的方法一样:

    # -*- coding:utf-8 -*-
    Student = type(
        "Student",
        # 元组只有单个元素后面需要加逗号!
        (object,),
        {
            'country':"China",
            'add':lambda self,x,y:x+y
        }
    )
    
    s1 = Student()
    print(s1.country)
    print(s1.add(12,33))

    不过,我最近看公司某个封装好的功能的源码的时候,发现了它另外的一个用途,就是“在对象方法中调用类方法”(什么,你分不清对象方法、类方法与静态方法?请自行Google)。

    在对象方法中使用类方法

    基本操作

    假设我们现在有一个Student类,要在对象方法中调用类方法,可以这样写:

    # -*- coding:utf-8 -*-
    class Student(object):
    
        @classmethod
        def get_country(cls):
            return "China"
    
        def __init__(self,name):
            self.name = name
            # type(self),在对象方法中使用类的方法
            self.country = type(self).get_country()
    
        def get_my_country(self):
            # type(self),在对象方法中使用类的方法
            return type(self).get_country()
    
    if __name__ == '__main__':
        
        s1 = Student('wanghw')
        
        print(s1.country) # China
        print(s1.get_my_country()) # China
        
        # 事实上,对象也可以直接调用“类方法”,但是为了“规范”,我们不这么直接让对象直接调用“类方法”
        print(s1.get_country()) # China

    起一个与类方法同名的对象方法再试试

    上面的基本操作也许大家都明白,现在我们试一下极端的方式:起一个与类方法同名的对象方法,看看效果如何:

    # -*- coding:utf-8 -*-
    class Student(object):
    
        @classmethod
        def get_country(cls):
            return "China"
    
        def __init__(self,name):
            self.name = name
            # type(self),在对象方法中使用类的方法
            self.country = type(self).get_country()
    
        def get_my_country(self):
            # type(self),在对象方法中使用类的方法
            return type(self).get_country()
    
        # 起一个与类方法同名的对象方法
        def get_country(self):
            return "English"
    
    
    if __name__ == '__main__':
    
        s1 = Student('wanghw')
    
        print(s1.country) 
        print(s1.get_my_country())

    运行程序,你会发现上报了一个这样的错误:

    TypeError: get_country() missing 1 required positional argument: 'self'

    实际上,此时我们实例化的Student对象用的是自己的方法!而上面的__init__初始化方法与get_my_country方法的调用者是类Student,缺少了参数self,我们把程序修改如下(在get_country中加上参数self再试试):

    # -*- coding:utf-8 -*-
    class Student(object):
    
        @classmethod
        def get_country(cls):
            return "China"
    
        def __init__(self,name):
            self.name = name
            # type(self),在对象方法中使用类的方法
            self.country = type(self).get_country(self)
    
        def get_my_country(self):
            # type(self),在对象方法中使用类的方法
            return type(self).get_country(self)
    
        # 起一个与类方法同名的对象方法
        def get_country(self):
            return "English"
    
    
    if __name__ == '__main__':
    
        s1 = Student('wanghw')
    
        print(s1.country) # English
        print(s1.get_my_country()) # English

    由此,我们可以得出结论:如果对象方法与类方法同名的话,对象会优先调用自己的方法!

    其他相关的知识点详见这篇博客

    其他关于type的说明,我自己之前总结过一篇关于type与isinstance的区别的文章,还有我在网上找的一篇很不错的关于type的说明的文章:

    https://www.cnblogs.com/paulwhw/p/10637282.html

    https://www.cnblogs.com/zy0517/articles/9046549.html

  • 相关阅读:
    2019 牛客多校第二场 H Second Large Rectangle
    2019 牛客多校题解目录
    2019 牛客多校第一场 F Random Point in Triangle
    2019 牛客多校第一场 E ABBA
    2019 牛客多校第一场 D Parity of Tuples
    2019 牛客多校第一场 C Euclidean Distance ?
    2019 牛客多校第一场 B Integration
    2019 牛客多校第一场 A Equivalent Prefixes
    Sigils of Elohim
    UVA 1599 Ideal Path
  • 原文地址:https://www.cnblogs.com/paulwhw/p/11807501.html
Copyright © 2011-2022 走看看