Python反射机制与内置魔法方法详解

周予安
周予安
发布时间:2026-10-13| 5人浏览过
原创

本文深入解析Python中的反射机制与常用内置方法重写。详细讲解isinstance、issubclass等类型检查函数,以及hasattr、getattr、setattr、delattr四个核心反射操作。同时涵盖__new__、__call__、__len__、__hash__、__eq__等魔法方法的实现原理与应用场景,结合单例模式、对象调用及集合去重等实例,帮助开发者掌握Python面向对象的高级编程技巧。

本文详细介绍Python中的反射机制及内置方法重写技术,旨在为读者提供实用的参考案例。

类型检查函数:isinstance与issubclass

使用isinstance(obj,cls)可以判断对象obj是否属于类cls的实例,其功能类似于type()。

class Foo(object):
  pass
obj = Foo()
isinstance(obj, Foo)

使用issubclass(sub, super)用于检测子类sub是否为super类的派生类。

class Foo(object):
 pass
class Bar(Foo):
 pass
issubclass(Bar, Foo)

反射机制概述

1. 反射的定义

反射概念由Smith在1982年首次提出,指程序具备访问、检测并修改自身状态或行为的能力(即自省)。该概念迅速引发计算机科学界对反射应用的研究,并率先在Lisp及面向对象编程语言中取得显著成果。

四大核心反射函数

hasattr(obj,str)
用于检测对象是否包含指定属性。

getattr(obj,str)
用于获取属性值,若属性不存在则引发错误。

setattr(obj,str,value)
用于设置属性值。

delattr(obj,str)
用于删除属性,若属性不存在则引发错误。

通过导入其他模块,可利用反射机制查找该模块中是否存在特定方法。

def test():
 print('from the test')

对象索引系列方法

__getitem__\__setitem__\__delitem__

class Foo:
 def __init__(self,name):
  self.name=name
 def __getitem__(self, item):
  print(self.__dict__[item])
 def __setitem__(self, key, value):
  self.__dict__[key]=value
 def __delitem__(self, key):
  print('del obj[key]时,我执行')
  self.__dict__.pop(key)
 def __delattr__(self, item):
  print('del obj.key时,我执行')
  self.__dict__.pop(item)
f1=Foo('sb')
f1['age']=18
f1['age1']=19
del f1.age1
del f1['age']
f1['name']='alex'
print(f1.__dict__)

运行结果示例:

当执行del obj.key时,触发以下逻辑: 当执行del obj[key]时,触发以下逻辑: {'name': 'alex'}

构造方法__new__

class A:
 def __init__(self):
  self.x = 1
  print('in init function')
 def __new__(cls, *args, **kwargs):
  print('in new function')
  return object.__new__(A, *args, **kwargs)
a = A()
print(a.x)

运行结果示例:

in new function in init function 1

单例模式实现示例:

class A:
 def __new__(cls):
  if not hasattr(cls,'obj'):
   cls.obj = object.__new__(cls)
  return cls.obj
a = A()
b = A()
print(a is b)

运行结果示例:

True

调用方法__call__

在对象后添加括号将触发执行。

注意:构造方法的执行由对象创建触发,即:对象 = 类名();而__call__方法的执行由对象后加括号触发,即:对象() 或 类()()。

class Foo:
 def __init__(self):
  pass
 def __call__(self, *args, **kwargs):
  print('__call__')
obj = Foo() # 执行 __init__
obj()  # 执行 __call__

运行输出示例:

__call__

长度方法__len__

class A:
 def __init__(self):
  self.a = 1
  self.b = 2
 def __len__(self):
  return len(self.__dict__)
a = A()
print(len(a))

运行结果示例:

2

哈希方法__hash__

class A:
 def __init__(self):
  self.a = 1
  self.b = 2
 def __hash__(self):
  return hash(str(self.a)+str(self.b))
a = A()
print(hash(a))

运行结果示例:

-1777982230

相等性判断__eq__

class A:
 def __init__(self):
  self.a = 1
  self.b = 2
 def __eq__(self,obj):
  if self.a == obj.a and self.b == obj.b:
   return True
a = A()
b = A()
print(a == b)

运行结果示例:

True

合并姓名与性别相同的人员:

class Person:
 def __init__(self,name,age,sex):
  self.name = name
  self.age = age
  self.sex = sex
 def __hash__(self):
  return hash(self.name+self.sex)
 def __eq__(self, other):
  if self.name == other.name and self.sex == other.sex:return True
p_lst = []
for i in range(84):
 p_lst.append(Person('egon',i,'male'))
print(p_lst)
print(set(p_lst))

运行结果示例:

[<__main__.Person object at 0x01425AB0>, <__main__.Person object at 0x01425AD0>, <__main__.Person object at 0x01425AF0>, <__main__.Person object at 0x01425910>, <__main__.Person object at 0x014258D0>, <__main__.Person object at 0x01425950>, <__main__.Person object at 0x01425970>, <__main__.Person object at 0x014259D0>, <__main__.Person object at 0x01425C70>, <__main__.Person object at 0x01425890>, <__main__.Person object at 0x01425B30>, <__main__.Person object at 0x01425BB0>, <__main__.Person object at 0x01425C30>, <__main__.Person object at 0x01429710>, <__main__.Person object at 0x01429730>, <__main__.Person object at 0x014298F0>, <__main__.Person object at 0x01429910>, <__main__.Person object at 0x01429930>, <__main__.Person object at 0x01429950>, <__main__.Person object at 0x01429970>, <__main__.Person object at 0x01429990>, <__main__.Person object at 0x014299B0>, <__main__.Person object at 0x014299D0>, <__main__.Person object at 0x014299F0>, <__main__.Person object at 0x01429A10>, <__main__.Person object at 0x01429A30>, <__main__.Person object at 0x01429A50>, <__main__.Person object at 0x01429A70>, <__main__.Person object at 0x01429A90>, <__main__.Person object at 0x01429AB0>, <__main__.Person object at 0x01429AD0>, <__main__.Person object at 0x01429AF0>, <__main__.Person object at 0x01429B10>, <__main__.Person object at 0x01429B30>, <__main__.Person object at 0x01429B50>, <__main__.Person object at 0x01429B70>, <__main__.Person object at 0x01429B90>, <__main__.Person object at 0x01429BB0>, <__main__.Person object at 0x01429BD0>, <__main__.Person object at 0x01429BF0>, <__main__.Person object at 0x01429C10>, <__main__.Person object at 0x01429C30>, <__main__.Person object at 0x01429C50>, <__main__.Person object at 0x01429C70>, <__main__.Person object at 0x01429C90>, <__main__.Person object at 0x01429CB0>, <__main__.Person object at 0x01429CD0>, <__main__.Person object at 0x01429CF0>, <__main__.Person object at 0x01429D10>, <__main__.Person object at 0x01429D30>, <__main__.Person object at 0x01429D50>, <__main__.Person object at 0x01429D70>, <__main__.Person object at 0x01429D90>, <__main__.Person object at 0x01429DB0>, <__main__.Person object at 0x01429DD0>, <__main__.Person object at 0x01429DF0>, <__main__.Person object at 0x01429E10>, <__main__.Person object at 0x01429E30>, <__main__.Person object at 0x01429E50>, <__main__.Person object at 0x01429E70>, <__main__.Person object at 0x01429E90>, <__main__.Person object at 0x01429EB0>, <__main__.Person object at 0x01429ED0>, <__main__.Person object at 0x01429EF0>, <__main__.Person object at 0x01429F10>, <__main__.Person object at 0x01429F30>, <__main__.Person object at 0x01429F50>, <__main__.Person object at 0x01429F70>, <__main__.Person object at 0x01429F90>, <__main__.Person object at 0x01429FB0>, <__main__.Person object at 0x01429FD0>, <__main__.Person object at 0x01429FF0>, <__main__.Person object at 0x01751030>, <__main__.Person object at 0x01751050>, <__main__.Person object at 0x01751070>, <__main__.Person object at 0x01751090>, <__main__.Person object at 0x017510B0>, <__main__.Person object at 0x017510D0>, <__main__.Person object at 0x017510F0>, <__main__.Person object at 0x01751110>, <__main__.Person object at 0x01751130>, <__main__.Person object at 0x01751150>, <__main__.Person object at 0x01751170>, <__main__.Person object at 0x01751190>] {<__main__.Person object at 0x01425AB0>}

更多关于Python相关内容感兴趣的读者可查看本站专题:《Python面向对象程序设计入门与进阶教程》、《Python数据结构与算法教程》、《Python函数使用技巧总结》、《Python字符串操作技巧汇总》、《Python编码操作技巧总结》及《Python入门与进阶经典教程》

希望本文所述对大家Python程序设计有所帮助。

免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。

Python 相关产品和应用

全部下载
Selenium

Selenium

4.51.0 · Windows

用于浏览器自动化和 Web 测试的 Python 工具。

scikit-learn

scikit-learn

1.9.1 · Windows

常用 Python 机器学习算法与模型评估工具库。

Black

Black

26.10.1 · Windows

强调一致性的 Python 自动代码格式化工具。

Ruff

Ruff

0.17.1 · macOS

由 Rust 编写的高速 Python 代码检查和格式化工具。

pytest

pytest

9.1.1 · Windows

简洁而强大的 Python 自动化测试框架。

FastAPI

FastAPI

0.146.0 · Windows

高性能 Python API 框架,支持类型提示和自动接口文档。

Flask

Flask

3.1.3 · Windows

轻量灵活的 Python Web 应用框架。

Django

Django

6.1.2 · Windows

成熟的 Python Web 框架,适合构建内容站点和业务系统。

Spyder

Spyder

6.1.7 · Windows

面向科学计算与数据分析的 Python 集成开发环境。

SciPy

SciPy

1.18.1 · Windows

面向科学、工程和技术计算的 Python 算法库。