Skip to content

黑魔法

上下文管理

from contextlib import contextmanager

@contextmanager
def managed_resource(value):
    try:
        print(f"Acquiring resource with {value}")
        yield value
    finally:
        print("Releasing resource")

with managed_resource(42) as resource:
    print(f"Using resource: {resource}")
# 输出:
# Acquiring resource with 42
# Using resource: 42
# Releasing resource


class MyContextManager:
    def __enter__(self):
        print("Entering context")
        return self

    def __exit__(self, exc_type, exc_value, traceback):
        print("Exiting context")

with MyContextManager() as cm:
    print("Inside context")
# 输出:
# Entering context
# Inside context
# Exiting context

重定向标准输出

from contextlib import redirect_stdout
import io

f = io.StringIO()
with redirect_stdout(f):
    print("This goes to the stringIO object")
output = f.getvalue()
print(output)  # 输出: This goes to the stringIO object

生成器


def sub_generator():
    yield 1
    yield 2

def main_generator():
    yield from sub_generator()
    yield 3
    yield 4

for value in main_generator():
    print(value)  # 输出: 1 2 3 4

函数缓存

from functools import lru_cache

# 可以缓存函数的结果,避免重复计算,适用于计算密集型或I/O密集型函数。
@lru_cache(maxsize=None)
def fibonacci(n):
    if n < 2:
        return n
    return fibonacci(n-1) + fibonacci(n-2)

print(fibonacci(10))  # 输出: 55

slots

class Person:
    # 不能动态添加这两个属性外得属性
    __slots__ = ('name', 'age')

    def __init__(self, name, age):
        self.name = name
        self.age = age

控制属性访问


class DynamicAttributes:
    def __getattr__(self, name):
        if name.startswith('custom_'):
            return f"Custom attribute: {name}"
        raise AttributeError(f"{name} is not a valid attribute")

    def __setattr__(self, name, value):
        if name.startswith('custom_'):
            super().__setattr__(name, value)
        else:
            raise AttributeError(f"Cannot set attribute {name}")

dyn = DynamicAttributes()
print(dyn.custom_attribute)  # 输出: Custom attribute: custom_attribute
dyn.custom_attribute = 42
print(dyn.custom_attribute)  # 输出: 42

元编程

class MyMeta(type):
    def __new__(cls, name, bases, dct):
        print(f"Creating class {name}")
        return super().__new__(cls, name, bases, dct)

class MyClass(metaclass=MyMeta):
    pass

# 输出: Creating class MyClass

自定义字典行为

class DefaultDict(dict):
    # 自定义字典在访问不存在的键时的行为
    def __missing__(self, key):
        return f"Key {key} not found"

d = DefaultDict()
print(d['missing_key'])  # 输出: Key missing_key not found

inspect

import inspect

def example_function():
    pass

print(inspect.getsource(example_function))  # 输出: example_function 的源代码
print(inspect.signature(example_function))  # 输出: example_function 的签名

# 还可以获取函数得字符串代码等

枚举

from enum import Enum, auto

class Color(Enum):
    RED = auto()
    GREEN = auto()
    BLUE = auto()

print(Color.RED)  # 输出: Color.RED
print(Color.RED.value)  # 输出: 1

数据类

from dataclasses import dataclass, field

# 简洁的方式来定义具有默认值和自动生成的特殊方法的类
@dataclass
class Person:
    name: str
    age: int
    hobbies: list = field(default_factory=list)

alice = Person('Alice', 30)
print(alice)  # 输出: Person(name='Alice', age=30, hobbies=[])

排列组合及生成

import itertools

# 组合函数
letters = ['a', 'b', 'c']
combinations = list(itertools.combinations(letters, 2))
print(combinations)  # 输出: [('a', 'b'), ('a', 'c'), ('b', 'c')]

# 排列函数
permutations = list(itertools.permutations(letters, 2))
print(permutations)  # 输出: [('a', 'b'), ('a', 'c'), ('b', 'a'), ('b', 'c'), ('c', 'a'), ('c', 'b')]

# 生成笛卡尔积
letters = ['a', 'b']
numbers = [1, 2]
numbers1 = [1, 2]
cartesian_product = list(itertools.product(letters, numbers,numbers1))
print(cartesian_product)  # 输出: [('a', 1, 1), ('a', 1, 2), ('a', 2, 1), ('a', 2, 2), ('b', 1, 1), ('b', 1, 2), ('b', 2, 1), ('b', 2, 2)]

# 重复
repeated = itertools.repeat(10, 5)
print(list(repeated))  # 输出: [10, 10, 10, 10, 10]

# 循环
iterable = [1, 2, 3]
cycled = itertools.cycle(iterable)
for _ in range(10):
    print(next(cycled), end=' ')  # 输出: 1 2 3 1 2 3 1 2 3 1

# 链接
iter1 = [1, 2, 3]
iter2 = ['a', 'b', 'c']
result = list(itertools.chain(iter1, iter2))
print(result)  # 输出: [1, 2, 3, 'a', 'b', 'c']


手动gc

import gc

gc.collect()  # 手动触发垃圾回收
print(gc.get_count())  # 输出当前垃圾回收计数
print(gc.get_threshold())  # 输出垃圾回收阈值

对象格式化

class Person:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def __str__(self):
        return f"{self.name}, {self.age} years old"

p = Person('Alice', 30)
print(str(p))  # 输出: Alice, 30 years old




class Person:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def __format__(self, format_spec):
        if format_spec == 'full':
            return f"Name: {self.name}, Age: {self.age}"
        elif format_spec == 'short':
            return f"{self.name}"
        else:
            raise ValueError("Unknown format spec")

p = Person('Alice', 30)
print(f"{p:full}")  # 输出: Name: Alice, Age: 30
print(f"{p:short}")  # 输出: Alice

类运算



# __sub__ 方法
# 定义: __sub__(self, other)
# 用途: 定义对象自身作为左操作数时的减法行为。
# 调用时机: 当执行 a - b 时,如果 a 是一个定义了 __sub__ 方法的对象,Python 会调用 a.__sub__(b)。

# __rsub__ 方法
# 定义: __rsub__(self, other)
# 用途: 定义对象自身作为右操作数时的减法行为。
# 调用时机: 当执行 a - b 时,如果 a 没有定义 __sub__ 方法或 a.__sub__(b) 返回 NotImplemented,而 b 定义了 __rsub__ 方法,Python 会调用 b.__rsub__(a)。

class CustomNumber:
    def __init__(self, value):
        """
        初始化 CustomNumber 实例,设置其值。
        """
        self.value = value

    def __add__(self, other):
        """
        定义加法操作符 `+` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值相加的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value + other.value)
        return NotImplemented

    def __radd__(self, other):
        """
        定义反射加法操作符 `+` 的行为。
        当左操作数不支持加法时,调用此方法。
        """
        return CustomNumber(other + self.value)

    def __sub__(self, other):
        """
        定义减法操作符 `-` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值相减的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value - other.value)
        return NotImplemented

    def __rsub__(self, other):
        """
        定义反射减法操作符 `-` 的行为。
        当左操作数不支持减法时,调用此方法。
        """
        return CustomNumber(other - self.value)

    def __mul__(self, other):
        """
        定义乘法操作符 `*` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值相乘的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value * other.value)
        return NotImplemented

    def __rmul__(self, other):
        """
        定义反射乘法操作符 `*` 的行为。
        当左操作数不支持乘法时,调用此方法。
        """
        return CustomNumber(other * self.value)

    def __truediv__(self, other):
        """
        定义真除法操作符 `/` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值相除的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value / other.value)
        return NotImplemented

    def __rtruediv__(self, other):
        """
        定义反射真除法操作符 `/` 的行为。
        当左操作数不支持真除法时,调用此方法。
        """
        return CustomNumber(other / self.value)

    def __floordiv__(self, other):
        """
        定义整除操作符 `//` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值整除的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value // other.value)
        return NotImplemented

    def __rfloordiv__(self, other):
        """
        定义反射整除操作符 `//` 的行为。
        当左操作数不支持整除时,调用此方法。
        """
        return CustomNumber(other // self.value)

    def __mod__(self, other):
        """
        定义取模操作符 `%` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值取模的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value % other.value)
        return NotImplemented

    def __rmod__(self, other):
        """
        定义反射取模操作符 `%` 的行为。
        当左操作数不支持取模时,调用此方法。
        """
        return CustomNumber(other % self.value)

    def __pow__(self, other):
        """
        定义幂运算操作符 `**` 的行为。
        如果 other 是 CustomNumber 类型,则返回两个实例值幂运算的新 CustomNumber 实例。
        """
        if isinstance(other, CustomNumber):
            return CustomNumber(self.value ** other.value)
        return NotImplemented

    def __rpow__(self, other):
        """
        定义反射幂运算操作符 `**` 的行为。
        当左操作数不支持幂运算时,调用此方法。
        """
        return CustomNumber(other ** self.value)

    def __str__(self):
        """
        返回 CustomNumber 实例的字符串表示。
        """
        return str(self.value)

# 示例用法
a = CustomNumber(10)
b = CustomNumber(3)

print(a + b)  # 输出: 13
print(a - b)  # 输出: 7
print(a * b)  # 输出: 30
print(a / b)  # 输出: 3.3333333333333335
print(a // b)  # 输出: 3
print(a % b)  # 输出: 1
print(a ** b)  # 输出: 1000

zip

list1 = [1, 2, 3]
list2 = ['a', 'b', 'c']
zipped = zip(list1, list2)
print(list(zipped))  # 输出: [(1, 'a'), (2, 'b'), (3, 'c')]

for idx, (num, char) in enumerate(zip(list1, list2)):
    print(f'Index: {idx}, Number: {num}, Character: {char}')

my_dict = dict(zip(list1, list2))

zipped = [(1, 'a'), (2, 'b'), (3, 'c')]
list1, list2 = zip(*zipped)
print(list1)  # 输出: (1, 2, 3)
print(list2)  # 输出: ('a', 'b', 'c')