MST

星途 面试题库

面试题:Python多场景下禁止函数修改列表策略的优化

在Python的类方法、多线程环境以及函数装饰器等不同场景中,分别如何优化禁止函数修改列表的策略?请针对每个场景给出详细的代码示例和优化思路。
30.4万 热度难度
编程语言Python

知识考点

AI 面试

面试题答案

一键面试

类方法场景

优化思路:在类方法中,可以通过对传入的列表进行拷贝,然后在方法内使用拷贝后的列表,这样就不会修改原始列表。 代码示例

class MyClass:
    @classmethod
    def my_class_method(cls, my_list):
        new_list = my_list.copy()
        # 对new_list进行操作,不会影响原始my_list
        new_list.append(1)
        return new_list


original_list = [1, 2, 3]
result = MyClass.my_class_method(original_list)
print(original_list)  # 输出: [1, 2, 3]
print(result)  # 输出: [1, 2, 3, 1]

多线程环境场景

优化思路:使用threading.Lock来保证在任何时刻只有一个线程可以访问和修改列表。同时可以将列表封装在一个类中,通过类的方法来操作列表,在方法内加锁。 代码示例

import threading


class SafeList:
    def __init__(self, initial_list):
        self.list = initial_list
        self.lock = threading.Lock()

    def append(self, value):
        with self.lock:
            new_list = self.list.copy()
            new_list.append(value)
            self.list = new_list

    def get_list(self):
        with self.lock:
            return self.list.copy()


safe_list = SafeList([1, 2, 3])


def thread_function():
    safe_list.append(4)


threads = []
for _ in range(5):
    t = threading.Thread(target=thread_function)
    threads.append(t)
    t.start()

for t in threads:
    t.join()

print(safe_list.get_list())  # 输出: [1, 2, 3, 4, 4, 4, 4, 4]

函数装饰器场景

优化思路:装饰器可以在函数调用前后进行处理,在函数调用前对列表进行拷贝,将拷贝后的列表传递给函数,函数返回后再对比是否有修改,如果有修改则抛出异常或者采取其他处理。 代码示例

def protect_list(func):
    def wrapper(*args, **kwargs):
        new_args = []
        for arg in args:
            if isinstance(arg, list):
                new_args.append(arg.copy())
            else:
                new_args.append(arg)
        new_kwargs = {}
        for key, value in kwargs.items():
            if isinstance(value, list):
                new_kwargs[key] = value.copy()
            else:
                new_kwargs[key] = value
        result = func(*new_args, **new_kwargs)
        return result

    return wrapper


@protect_list
def my_function(my_list):
    my_list.append(1)
    return my_list


original_list = [1, 2, 3]
result = my_function(original_list)
print(original_list)  # 输出: [1, 2, 3]
print(result)  # 输出: [1, 2, 3, 1]