
在Python中,__init__ 和 __call__ 是两个特殊的方法,它们在类的上下文中有特定的用途:
__init__方法:
- 这是类的初始化方法,当一个实例被创建时,它会被自动调用。
- 它通常用于接收初始化参数并设置实例的初始状态。
- 在你的示例中,
FixedContentQueryChecker类的__init__方法接收一个参数fixed_content,并将其存储在实例变量self.fixed_content中。这个变量随后可以在类的其他方法中使用。
__call__方法:
- 当一个实例被用作函数时,
__call__方法会被自动调用。 - 这意味着如果你有一个类的实例,并且你像调用函数一样调用这个实例(即
instance()),Python 会寻找并执行__call__方法。 - 在你的示例中,
__call__方法定义了FixedContentQueryChecker类的行为,使其可以像函数一样被调用。它接收一个参数q,这是一个字符串,默认为空字符串。方法内部检查self.fixed_content是否为q的子串,如果是,则返回True,否则返回False。
from typing import Annotated
from fastapi import Depends, FastAPI
app = FastAPI()
class FixedContentQueryChecker:
def __init__(self, fixed_content: str):
self.fixed_content = fixed_content
def __call__(self, q: str = ""):
if q:
return self.fixed_content in q
return False
checker = FixedContentQueryChecker("bar")
@app.get("/query-checker/")
async def read_query_check(fixed_content_included: Annotated[bool, Depends(checker)]):
return {"fixed_content_in_query": fixed_content_included}在你的FastAPI应用示例中,FixedContentQueryChecker 类被用作一个依赖项,它检查查询参数中是否包含特定的固定内容。这里是详细步骤:
FixedContentQueryChecker类被实例化为checker,初始化时传入了字符串"bar"。- 在FastAPI路由装饰器
@app.get("/query-checker/")下,定义了一个异步视图函数read_query_check。 - 这个视图函数使用了一个依赖项
Annotated[bool, Depends(checker)],它告诉FastAPI在调用视图函数之前,先调用checker实例(即调用它的__call__方法)。 - 依赖项的参数
q默认为空字符串,但FastAPI会将查询参数q的值传递给checker实例。 checker实例的__call__方法检查传递给它的查询参数q是否包含"bar"字符串,并将结果作为fixed_content_included参数传递给read_query_check视图函数。- 视图函数返回一个字典,包含一个键
fixed_content_in_query,其值是checker实例检查的结果。
这样,当用户发送GET请求到 /query-checker/ 并提供查询参数 q 时,FastAPI会调用 checker 实例来检查 q 是否包含 "bar",并将结果作为JSON响应返回。
补课:
在Python中,当你想让一个类的实例表现得像一个函数时,你可以在类定义中实现 __call__ 方法。这个方法在实例被调用(使用圆括号 ())时自动触发。这使得对象可以采用类似函数的调用方式。
下面是一个简单的例子,演示如何使用 __call__ 方法:
class Greeting:
def __init__(self, name):
self.name = name
def __call__(self):
return f"Hello, {self.name}!"
# 创建一个Greeting类的实例
greeter = Greeting("World")
# 调用这个实例,就像它是一个函数一样
print(greeter()) # 输出: Hello, World!创建一个类的实例跟调用实例是不一样的。
在这个例子中,Greeting 类有一个 __init__ 方法来初始化实例,接收一个名字 name。__call__ 方法则定义了当实例被调用时应该执行的操作,这里是返回一个问候语。
另一个例子:创建一个简单的计算器
让我们创建一个可以像函数一样调用的简单计算器类:
class Calculator:
def __init__(self, a=0, b=0):
self.a = a
self.b = b
def __call__(self, operation):
if operation == "add":
return self.a + self.b
elif operation == "subtract":
return self.a - self.b
elif operation == "multiply":
return self.a * self.b
elif operation == "divide":
if self.b != 0:
return self.a / self.b
else:
return "Error: Division by zero"
# 创建一个Calculator实例
calc = Calculator(10, 5)
# 调用实例来执行加法
print(calc("add")) # 输出: 15
# 调用实例来执行减法
print(calc("subtract")) # 输出: 5
# 调用实例来执行乘法
print(calc("multiply")) # 输出: 50
# 调用实例来执行除法
print(calc("divide")) # 输出: 2.0
# 尝试除以零
print(calc("divide")) # 输出: Error: Division by zero在这个例子中,Calculator 类的 __call__ 方法接收一个操作参数 operation,根据传入的操作类型(加法、减法、乘法、除法),执行相应的运算。
通过实现 __call__ 方法,类的实例可以被直接调用,这使得它们在某些情况下非常有用,特别是在需要自定义函数对象或实现回调函数时。









