python 类中方法总结 --- 实例方法、类方法、静态方法
在python的类语法中,可以出现三种方法,具体如下:
(1)实例方法
很多人学习python,不知道从何学起。
很多人学习python,掌握了基本语法过后,不知道在哪里寻找案例上手。
很多已经做案例的人,却不知道如何去学习更加高深的知识。
那么针对这三类人,我给大家提供一个好的学习平台,免费领取视频教程,电子书籍,以及课程的源代码!
QQ群:1097524789
1)第一个参数必须是实例本身,一般使用【self】表示。
2)在实例方法中,可以通过【self】来操作实例属性,【类名】来操作类属性。
3)实例方法只能通过实例对象去调用,尽管也可以通过类名间接调用【类名.方法名(self, ...)】,但此时仍然需要传入self对象。
(2)类方法
1)使用【@classmethod】修饰函数,且第一个参数必须是类本身,一般使用【cls】表示。
2)在类方法中,可以使用【cls=类名】来操作类属性,但是不能操作实例属性(self对象中存储的变量)。
3)类方法可以通过实例对象或者类对象调用。
(3)静态方法
1)使用【@staticmethod】修饰函数,不需要使用任何参数表示。与普通函数一样,只是将该方法放到了类中实现而已。
2)使用方式与类方法一样,参考类方法中的 2)、3)。(注:静态方法只能通过【类名】去操作类属性;)
案例1:实例方法、类方法、静态方法使用
class Foo(object):"""类三种方法语法形式"""count = 0 # 统计实例对象的数量class_method_count = 0 # 统计类方法的调用次数# 实例方法def __init__(self, name):self.name = nameFoo.count += 1# 实例方法def instance_method(self):print("是类{}的实例方法,只能被实例对象调用".format(Foo))print("产生了一个<{}>实例,共有<{}>个实例对象".format(self.name, Foo.count))# 类方法@classmethoddef class_method(cls):print("是类{}的类方法,可以被实例对象、类对象调用".format(cls))cls.__static_method_test()cls.class_method_count += 1# 静态方法@staticmethoddef static_method():print("是类{}的静态方法,可以被实例对象、类对象调用".format(Foo))print("+++以下内容为类方法class_method()的运行结果:")Foo.class_method()@staticmethoddef __static_method_test():print("调用了静态方法 static_method_test()")print("--"*20 + "实例方法测试" + "--"*20) obj1 = Foo("dog") obj1.instance_method() # <=> Foo.instance_method(obj1)print("--"*20 + "类方法测试" + "--"*20) obj1.class_method() print("--"*20) Foo.class_method()print("--"*20 + "静态方法测试" + "--" * 20) obj1.static_method() print("--"*20) Foo.static_method()""" 运行结果: ----------------------------------------实例方法测试---------------------------------------- 是类<class '__main__.Foo'>的实例方法,只能被实例对象调用 产生了一个<dog>实例,共有<1>个实例对象 ----------------------------------------类方法测试---------------------------------------- 是类<class '__main__.Foo'>的类方法,可以被实例对象、类对象调用 调用了静态方法 static_method_test() ---------------------------------------- 是类<class '__main__.Foo'>的类方法,可以被实例对象、类对象调用 调用了静态方法 static_method_test() ----------------------------------------静态方法测试---------------------------------------- 是类<class '__main__.Foo'>的静态方法,可以被实例对象、类对象调用 +++以下内容为类方法class_method()的运行结果: 是类<class '__main__.Foo'>的类方法,可以被实例对象、类对象调用 调用了静态方法 static_method_test() ---------------------------------------- 是类<class '__main__.Foo'>的静态方法,可以被实例对象、类对象调用 +++以下内容为类方法class_method()的运行结果: 是类<class '__main__.Foo'>的类方法,可以被实例对象、类对象调用 调用了静态方法 static_method_test() """
从案例1中得到,类方法与静态方法可以相互调用,但是静态方法只能用【类名】表示,而类方法用【cls】就比较方便了。
案例2:实例方法、类方法、静态方法在继承中(子类重写父类中的方法)的使用
class Foo(object):X = 1Y = 14@staticmethoddef average(*mixes):print("父类中的静态方法 average(*mixes)")print("*****", mixes)return sum(mixes) / len(mixes)@staticmethoddef static_method():print("父类中的静态方法 static_method()")return Foo.average(Foo.X, Foo.Y) # 注:因为这儿已经限定了只允许调用父类中的average()@classmethoddef class_method(cls): # 父类中的类方法print("父类中的类方法 class_method(cls)")return cls.average(cls.X, cls.Y) # 注:若用子类对象调用该函数,此时的cls==Son,故调用子类重写后的average()class Son(Foo):@staticmethoddef average(*mixes): # "子类中重载了父类的静态方法"print("子类中重载了父类的静态方法 average(*mixes)")print("*****", mixes)return sum(mixes) / len(mixes)print(Son.average(1, 2, 3), "\n" + "---" * 20) print(Son.class_method(), "\n" + "---" * 20) print(Son.static_method(), "\n" + "---" * 20)""" 运行结果: ------------------------------------------------------------ 子类中重载了父类的静态方法 average(*mixes) ***** (1, 2, 3) 2.0 ------------------------------------------------------------ 父类中的类方法 class_method(cls) 子类中重载了父类的静态方法 average(*mixes) ***** (1, 14) 7.5 ------------------------------------------------------------ 父类中的静态方法 static_method() 父类中的静态方法 average(*mixes) ***** (1, 14) 7.5 ------------------------------------------------------------ """
从案例2中得到,子类对象调用父类中的 类方法 class_method(cls) 时,由于【cls】此时为【Son】,故会执行子类中的类方法、静态方法、静态属性;进一步推断出,类方法中【cls】取决于类方法的调用者,只有发生类方法调用后才能知道执行结果。而父类中静态方法 static_method()只能调用父类中类方法、静态方法、静态属性,与静态方法的调用者无关;进一步推断,静态方法可以提前预知程序的执行结果,如执行当前类中的某个类方法或静态方法。
对案例2做一个多态测试,添加代码如下:
def test_polymorphic(foo):"""多态测试:param foo: 父类对象:return: None"""print(f.average(1, 2, 3))f = Foo() test_polymorphic(f)print("----"*10) f = Son() # 会触发多态 test_polymorphic(f)""" 父类中的静态方法 average(*mixes) ***** (1, 2, 3) 2.0 ---------------------------------------- 子类中重载了父类的静态方法 average(*mixes) ***** (1, 2, 3) 2.0 """
继续做多态测试,添加代码如下:
def test_polymorphic(foo):"""多态测试:param foo: 父类对象:return: None"""print(f.class_method())f = Foo() test_polymorphic(f)print("----"*10) f = Son() # 会触发多态 test_polymorphic(f)""" 父类中的类方法 class_method(cls) 父类中的静态方法 average(*mixes) ***** (1, 14) 7.5 ---------------------------------------- 父类中的类方法 class_method(cls) 子类中重载了父类的静态方法 average(*mixes) ***** (1, 14) 7.5 """
案例3:使用类方法或静态方法初始化类(可以自定义类的初始方式)
class Book(object):def __init__(self, title):self.__title = title@classmethoddef object_create_by_class_method(cls, title_list):"""使用生产器实例化多个对象:param title_list: 每个对象的初始化参数,List:return:迭代器,每个实例化对象"""for title in title_list:yield cls(title=title)@staticmethoddef object_create_by_static_method(title_list): # 功能与类方法一样for title in title_list:yield Book(title=title)@propertydef title(self):return self.__title@title.setterdef title(self, value):if not isinstance(value, str):raise TypeError('%s must be str' % value)self.__title = value@title.deleterdef title(self):del self.__title# raise TypeError('Can not delete')books = ["Chinese", "mathematics", "English"] g_books = Book.object_create_by_class_method(books) print(g_books) # <generator object Book.object_create_by_class_method at 0x000001FB72AFEEC8>print(g_books.__next__().title) # 查看书的title -- Chinese print(g_books.__next__().title) # 查看书的title -- mathematicsbook = g_books.__next__() # 得到一个实例化对象print(book.title) # 查看书的title -- English print(book.__dict__) # {'_Book__title': 'English'}book.title = "英语" # 修改属性 print(book.title) # 查看书的title -- 英语 print(book.__dict__) # {'_Book__title': '英语'}del book.title # 删除属性 print(book.__dict__) # {}
从案例3中得到,使用类方法或者静态方法可以自定义类的初始化方式,本案例中实现的功能是使用生产器批量创建多个对象。同时,案列中使用了【property】属性,property的作用相当于执行了某个函数,并获得该函数的返回值;其使用方式有3种,分别为【@property --- get】、【@函数名.setter --- set】、【@函数名.deleter --- del】,后二种必须在第一种使用的情况下才能使用,在表现形式上就是通过实例化对象间接访问属性。
最后,我们对案例3做微小改变,来看看实例方法、类方法、静态方法与类、对象之间的关系,代码如下:
class Book(object):@classmethoddef object_create_by_class_method(cls):pass@staticmethoddef object_create_by_static_method():passdef instance_method(self):passbook = Book() print(book.instance_method) # 方法(绑定到对象:发生调用时,将【实例对象=self】自动作为第一个参数传入实例方法中) print(book.object_create_by_class_method) # 方法(绑定到类:发生调用时,将【类=cls】自动作为第一个参数传入类方法中) print(book.object_create_by_static_method) # 普通函数(非绑定:发生调用时,不需要传入任何参数,如self,cls)print(Book.instance_method) # 普通函数(非绑定,因为实例方法就存储在类的命名空间中) print(Book.object_create_by_class_method) # 绑定到类 print(Book.object_create_by_static_method) # 普通函数(非绑定) """ <bound method Book.instance_method of <__main__.Book object at 0x000002481CEDE988>> <bound method Book.object_create_by_class_method of <class '__main__.Book'>> <function Book.object_create_by_static_method at 0x000002481D12C828><function Book.instance_method at 0x000002481D12C8B8> <bound method Book.object_create_by_class_method of <class '__main__.Book'>> <function Book.object_create_by_static_method at 0x000002481D12C828> """
可以发现,
1)类中的实例方法都绑定了实例对象,故建议使用实例对象调用实例方法;
2)类中的类方法都绑定了类,故建议使用类对象调用类方法,即使使用实例对象调用类方法,仍然自动将【类名】作为第一个参数传入类方法。
3)而对于静态方法而言,无论使用实例对象或者类对象调用其方法都不会自动进行参数传递,故不做限制。
4)若能用类解决的问题,就将类中的方法定义为类方法,这样可以避免实例化对象的开销。
python 类中方法总结 --- 实例方法、类方法、静态方法相关推荐
- python类中方法调用自己类的方法_python 类中方法总结 --- 实例方法、类方法、静态方法...
在python的类语法中,可以出现三种方法,具体如下: (1)实例方法 1)第一个参数必须是实例本身,一般使用[self]表示. 2)在实例方法中,可以通过[self]来操作实例属性,[类名]来操作类 ...
- python类中方法调用自己类的方法_python怎么调用类方法
python中的类用来描述具有相同的属性和方法的对象的集合.它定义了该集合中每个对象所共有的属性和方法.对象是类的实例. 要想调用类中的方法,首先要定义一个类,python中定义类使用class关键字 ...
- python类中方法的执行顺序-浅谈Python的方法解析顺序(MRO)
方法解析顺序, Method Resolution Order 从一段代码开始 考虑下面的情况: class A(object): def foo(self): print('A.foo()') cl ...
- python 类中方法的动态特性
2019独角兽企业重金招聘Python工程师标准>>> 方法添加 class Fruit(object): pass def add(self): print "grow ...
- python类中方法的执行顺序-Python实例化class的执行顺序实例方法
Python中实例化class的执行顺序示例详解 前言 本文主要介绍了关于Python实例化class的执行顺序的相关内容,下面话不多说了,来一起看看详细的介绍吧 Python里对类的实例化时有怎样的 ...
- python类中方法的执行顺序-Python中实例化class的执行顺序示例详解
前言 本文主要介绍了关于Python实例化class的执行顺序的相关内容,下面话不多说了,来一起看看详细的介绍吧 Python里对类的实例化时有怎样的顺序 一般来说一个类里面有类变量和方法,比如我们定 ...
- python类中方法的执行顺序-python – 新式类中的方法解析顺序(MRO)?
在Python in a Nutshell(第2版)一书中有一个使用的例子 旧样式类,用于演示如何以经典分辨率顺序解析方法 它与新订单有何不同. 我通过重写新样式的示例尝试了相同的示例,但结果与使用旧 ...
- python预定义_【Python】python类中方法的预定义
知乎问题: 像这个图片里面显示的,self.prediction首先声明了下然后下面给出了定义,然后optimize又调用这个函数但是没有用self.prediction()这样的方式而是像用变量一样 ...
- python类中方法的执行顺序-python 函数或者类 代码的执行顺序
修改了一下问题,大家直接先看例 3 对于简单的控制语句来说, x = 1 if x > 0: print('true') else: print('false') 我们都知道当判定 x > ...
最新文章
- ORACLE11g 前期安装环境配置
- 【高并发】面试官:说说缓存最关心的问题?有哪些类型?回收策略和算法?...
- 使用图片方式自定义iOS导航栏navigationItem的backBarButtonItem
- Machine Learning - Andrew Ng on Coursera (Week 3)
- 熔断器---Hystrix
- mui几种页面跳转方式对比
- 10种C++排序算法
- 微信小程序的多选改变样式_微信小程序radio的样式修改
- [Spark]Spark常用的优化方法
- 翻转一个数的二进制后的值
- 刚入职的阿里巴巴,我是怎么学习算法的
- 经典五笔(五笔输入法)
- XP系统安装打印机提示未安装打印机驱动程序,操作无法完成.
- Ubuntu-18.04安装
- 【Navicat】Navicat Premium12 下载、安装、激活、过期解决方法 —— 永久有效
- fabs () 函数
- Java实现hanoi塔
- 使用 Mailgun 配置 Ghost 邮箱
- ibatis mysql 函数_Ibatis+MySql范例(转)
- Chrome浏览器插件(扩展程序)获取以及安装