核心编程到底在学什么
很多人学完Python语法后仍写不出可靠的代码,问题往往不在语法,而在对语言机制的模糊理解。核心编程关注的是一组底层约定:对象如何创建与销毁、名字如何绑定、迭代如何驱动、异常如何传播。这些机制决定了代码行为,也决定了调试成本。
一切皆对象与名字绑定
Python中变量不是“装值的盒子”,而是贴在对象上的名字。a = [1, 2] 让名字 a 指向列表对象,b = a 只是增加一个指向同一对象的引用。理解这一点,就能解释为什么修改 b 会影响 a,而 a = a + [3] 却产生新对象。
由此引出可变与不可变的区别。整数、字符串、元组不可变,列表、字典、集合可变。把可变对象用作函数默认参数是经典陷阱:默认值只在定义时求值一次,多次调用会共享同一个对象。正确做法是用 None 作占位,在函数体内新建。
作用域与闭包
Python采用词法作用域,查找顺序为局部、闭包、全局、内置。函数内部赋值会让名字成为局部变量,若想修改外层变量需用 nonlocal 或 global 声明。闭包让内层函数记住外层变量,但要注意循环中创建函数时的延迟绑定问题,通常用默认参数固定当前值。
迭代协议与生成器
for 循环背后是迭代协议:先调用 iter() 得到迭代器,再反复调用 next() 直到抛出 StopIteration。任何实现 iter 与 next 的对象都能被遍历。
生成器用 yield 把函数变成惰性迭代器,适合处理大文件或无限序列。它按需产出数据,内存占用与数据总量无关。需要强调的是,生成器只能消费一次,重复遍历会得到空结果,这是初学者常犯的错误。
异常处理与资源管理
异常不是错误报告,而是控制流的一部分。捕获异常应尽量具体,避免裸 except 吞掉所有问题。try/except/else/finally 中,else 在无异常时执行,finally 无论成败都会运行。
资源管理更推荐上下文管理器。with open(...) as f 保证文件在离开代码块时关闭,即使中途抛出异常。自定义类实现 enter 与 exit 即可支持 with,这比手写 try/finally 更清晰。
写出可维护的代码
核心编程的落点是工程习惯:用不可变数据结构减少意外修改,用生成器控制内存,用上下文管理器管理资源,用明确的异常处理替代静默失败。把这些机制吃透,代码的边界行为才可预期,排查问题也不必靠猜测。