交互式爱情
dummy = lambda path: ( lambda x, y: ( lambda data: ([y for x in open(path, "r").readline().splitlines() for y in x])[ 0 ] )(min(data), max(data)))让我们把它分成几行。lamb1 = lambda data: ([y for x in open(path, "r").readline().splitlines() for y in x])[0] 这看起来不对——为什么不使用数据呢?下一个:lamb2 = lambda x, y: lamb1(min(data), max(data))lamb2使用 2 个参数进行调用lamb1- 的最小值和最大值data。从哪里来data的?为什么我们要将两个参数传递给只需要一个参数的 lambda?最后:dummy = lambda path: lamb2所以 dummy 是一个 lambda,当被调用时,返回 lambda lamb2。您从不调用lamb2,因此您不能期望它返回值。如果你确实调用了lamb2,你会得到一个错误。很难思考和调试单行代码,所以我们首先将其定义为常规函数。def dummy(path): lines = [int(x) for x in open(path, "r").readlines()] smallest = min(lines) largest = max(lines) return (smallest, largest)现在将每一行转换为 lambda:readfile = lambda file: [int(x) for x in open(file, "r").readlines()]minmax = lambda data: (min(data), max(data)dummy = lambda path: minmax(readfile(path))并加入这些 lambda:dummy = lambda path: (lambda data: (min(data), max(data)))((lambda file: [int(x) for x in open(file, "r").readlines()])(path))如果我设置data.txt为10023234920211然后将其运行为dummy("data.txt")我得到输出:(1, 2349)请注意,我们仍然有一个错误 - 我们没有进行适当的清理。我们打开一个文件,但从未关闭它。由于 CPython 实现的引用计数机制,这通常不是问题,但引用计数是一个实现细节,其他实现不会这样做。要解决这个问题,最好的方法是使用语句with:def dummy(path): with open(path, 'r') as f: lines = [int(x) for x in f.readlines()] smallest = min(lines) largest = max(lines) return (smallest, largest)但故意没有“with表达”。Python 的设计初衷并不是鼓励将所有内容都塞进一个大的单行表达式中。如果我们想编写大行话lambda并仍然进行适当的清理,最接近问题精神的解决方案是定义一个助手:def with_(resource, code): with resource as x: return code(x)然后我们就可以翻译了with open(path, 'r') as f: lines = [int(x) for x in f.readlines()]到lines = with_(open(path, 'r'), lambda f: [int(x) for x in f.readlines()])并将其融入到我们的大话中,dummy = lambda path: (lambda data: (min(data), max(data)))((lambda file: with_(open(path, 'r'), lambda f: [int(x) for x in f.readlines()]))(path))当我们这样做时,我们最好f直接迭代,而不是构建一个列表readlines,然后迭代它:dummy = lambda path: (lambda data: (min(data), max(data)))((lambda file: with_(open(path, 'r'), lambda f: [int(x) for x in f]))(path))