Python基础学习——类的方法绑定

前言

本篇记录了温习Python基础知识时针对类和实例的方法创建时遇到的问题


一、问题描述

Python是一种动态语言,在定义了class并且创建了一个class的实例之后,可以对该实例绑定任何的属性和方法。同样也可以对类进行属性和方法的绑定。但在运用不同方法对类或实例进行绑定时,遇到了一些小坑。主要是针对types模块里MethodType函数的理解、不同绑定方法原理解释。

二、实验实例及解释

1.公共代码

代码如下(示例):

class Student(object):         #创建的类
	pass

def set_age(self, age):        #需要绑定的方法
	self.age = age

2.使用MethodType(function, self)给实例绑定方法

代码如下(示例):

from types import MethodType

s = Student() #创建一个实例
s.set_age = MethodType(set_age, s) #给实例绑定方法
s.set_age(25) #调用方法
s.age #返回25

但如果我们对类绑定方法呢?先同样使用MethodType

Student.set_age = MethodType(set_age, Student)
s1 = Student()
s2 = Student()
s3 = Student()
s1.set_age(25)
s2.set_age(15)
s1.age #返回15
s2.age #返回15
s3.age #返回15

出现了问题!此时三个实例的age属性都是15.原因在于,MethodType的第二个参数是针对实例进行绑定方法的。此时Student不仅可以看作是s的class,可以看作是object的一个实例。MethodType为Student这个实例绑上了一个方法,这个方法也可以被其子类的实例使用,但是创建了一个link指向外部的方法,在其实例调用时修改的都是同一内存。也就是说,我们以为修改的age属性,都是在修改Student的一个属性(Student.age),s这些实例的属性也是指向这个内存的

3.直接把方法绑定到类

代码如下(示例):

Student.set_age = set_age 
s1 = Student()
s2 = Student()
s3 = Student()
s1.set_age(25)
s2.set_age(15)
s1.age #返回25
s2.age #返回15
s3.age #AttributeError: 'Student' object has no attribute 'age'

此时,等价于创建Student这个class时内部定义了方法


4. 扩展:类本身有设置age属性的方法

代码如下(示例):

class Student(object):
    def set_age_self(self,age):
        self.age = age
    pass
 
def set_age(self, age):
    self.age = age

s1 = Student()
s2 = Student()
s3 = Student()

Student.set_age = MethodType(set_age, Student)
s1.set_age_self(25)
s2.set_age(15)
s1.age #返回25
s2.age #返回15
s3.age #返回15
Student.age #返回15

可见,类内部定义的方法指向和通过MethodType绑定的方法指向不是同一个位置!

s2.set_age_self(35)
s1.age #返回25
s2.age #返回35
s3.age #返回15
Student.age #返回15

总结

本文章记录了对类进行绑定方法遇到的一些问题。总而言之,MethodType是对实例进行绑定方法,真正要对类绑定一个其实例都能使用(分别被各个实例分别互不干扰使用)的方法时,要么在内部直接定义,要么在外部直接定义。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值