Python 核心语法全解:从入门到面向对象实战(学习笔记)
一、数据存储与运算基础
变量与标识符
Python 的变量和其他语言不太一样,它不需要提前声明类型,直接赋值就行。相较于其他语言更简洁
python
student_name = "Alice" # 字符串
student_age = 20 # 整数
score = 95.5 # 浮点数
踩坑提醒: 变量命名千万别用中文或者拼音缩写,xm = "小明" 这种代码过两天自己都不知道 xm 是啥。
f-string 格式化输出
以前学过 % 格式化和 .format(),但 f-string 真的是最香的。可以直接在字符串里写变量
python
print(f"学生: {student_name}, 年龄: {student_age}")
避坑指南: 很多新手喜欢用 + 号拼接字符串和数字(比如 "年龄:" + 20),这会直接报 TypeError。Python 不会自动帮你把数字转成字符串,必须手动 str(20),或者干脆直接用 f-string。
运算符体系
and 是"两个都真才真",or 是"有一个真就真",not 是取反。多写几个 if 判断就熟了。
python
is_adult = True
has_id = True
if is_adult and has_id:
print("允许进入")
二、流程控制语句
分支结构 (If & Match)
if...elif...else 是基础中的基础,但写的时候要注意缩进!Python 靠缩进来区分代码块,少一个空格就报错,这很重要
python
score = 85
if score >= 90:
grade = "A"
elif score >= 80:
grade = "B"
else:
grade = "C"
避坑指南: 缩进报错 (IndentationError) 是新手最高频的错误之一。建议在 PyCharm 或 VS Code 里把设置统一为"4个空格缩进",并且开启"显示空白字符"功能,一眼就能看出问题。另外,写代码时注意切换输入法,中文的冒号 : 和引号 " " 也会直接导致语法报错。
Python 3.10 的 match 是个新东西,类似其他语言的 switch-case,写多分支的时候比一堆 elif 清爽很多。不过要注意版本,低于 3.10 用不了。
python
match grade:
case "A": print("优秀")
case "B": print("良好")
case _: print("其他")
循环结构 (While & For)
while 适合不知道要循环多少次的场景,比如"用户输入正确密码才退出"。for 适合已知次数的遍历。
重点提醒: range(1, 101) 是左闭右开的,也就是 1 到 100,不包含 101。
python
total = 0
for i in range(1, 101):
total += i
print(f"1-100的和为: {total}")
三、数据容器(核心重点)
容器特点对比
| 容器类型 | 符号 | 特点 | 典型场景 |
|---|---|---|---|
| 列表 List | [] |
有序、可变、可重复 | 存储学生名单、购物车 |
| 元组 Tuple | () |
有序、不可变 | 存储坐标、数据库记录 |
| 集合 Set | {} |
无序、不重复 | 数据去重、交集运算 |
| 字典 Dict | {k:v} |
键值对映射 | 存储用户信息、配置项 |
代码实战与避坑
列表推导式是 Python 的招牌语法,一行顶别人好几行
python
# 一行生成平方数列表
squares = [x**2 for x in range(5)]
# 结果: [0, 1, 4, 9, 16]
避坑指南:
- 索引越界 (
IndexError) :访问列表时,索引是从 0 开始的。一个有 5 个元素的列表,最大索引是 4,访问list[5]会直接报错。 - 字典取值崩溃 :直接用
dict["不存在的key"]取值,如果 key 不存在程序会崩溃。建议使用dict.get("key", "默认值"),这样即使 key 找不到,也能安全返回一个默认值,不会报错。 - 深浅拷贝问题 :在修改嵌套的列表或字典时,直接赋值(如
list_b = list_a)或者浅拷贝,可能会导致改了 B 的数据,A 也跟着变了。遇到复杂嵌套结构时,记得使用copy.deepcopy()。
字典操作也很高频,尤其是遍历的时候要用 .items(),不然拿不到值。
python
user_info = {"name": "Bob", "age": 25}
user_info["city"] = "Beijing" # 新增键值对
for key, value in user_info.items():
print(f"{key}: {value}")
四、函数基础与进阶
函数定义与不定长参数
函数就是把重复的代码打包,需要的时候直接调用。*args 可以接收任意多个位置参数,写工具函数的时候特别好用。
python
def calculate_sum(*args):
return sum(args)
print(calculate_sum(1, 2, 3, 4)) # 输出: 10
变量作用域与类型注解
局部变量和全局变量 这个概念一开始容易混。简单说:函数里面定义的变量,函数外面用不了;想在函数里改全局变量,得加 global。
避坑指南: 在函数内部试图修改全局变量(比如 count += 1),却忘记在函数开头声明 global count,会导致报错 UnboundLocalError。
经典大坑:可变默认参数 。定义函数时,如果把默认参数设置为可变对象(比如列表 def test(param=[])),会导致每次调用该函数时,它们实际上共享同一个列表。上一次的修改会影响下一次的结果,这种 Bug 非常难排查。正确做法 是将默认值设为 None,再在函数内部处理。
类型注解(Type Hints)虽然不强制,但我强烈建议养成习惯。加上之后 IDE 能给你智能提示,改代码的时候不容易出错。
python
def greet(name: str, times: int = 1) -> str:
return f"Hello {name}" * times
五、模块与包管理
代码写多了就会发现,全塞在一个文件里根本没法看。这时候就需要拆成模块和包。
import 导入现成的库,比如 random 生成随机数、time 处理时间。自己写的 .py 文件也可以被 import,这就是模块。
踩坑提醒: 包文件夹里一定要有 __init__.py 文件(哪怕是空的),不然 Python 不认它是包。这个问题我折腾了好久才搞明白。
python
import random
code = "".join([str(random.randint(0, 9)) for _ in range(4)])
print(f"验证码: {code}")
六、面向对象编程 (OOP)
说实话,OOP 是我整个语法阶段最难理解的部分。类、对象、封装、继承、多态......概念一堆,刚开始完全不知道在干嘛。
后来慢慢想通了:类就是图纸,对象就是根据图纸造出来的实物。比如"学生"是一个类,"张三"和"李四"就是两个对象。
核心概念
__init__:构造方法,创建对象时自动执行,用来初始化属性。__str__:定义print(对象)时显示什么内容。- 私有属性 :属性名前加双下划线
__,外部就不能直接访问了,这就是封装。
避坑指南(OOP 重灾区):
- 忘记写
self:在类的方法中,第一个参数必须是self,用于指向当前实例对象。初学者经常忘记写它,或者在类内部调用其他方法/属性时忘记加self.。 __init__拼写错误 :Python 的魔术方法前后都是双下划线,写成单下划线或者漏掉一个下划线,会导致初始化方法无法被自动调用。- 抽象概念难落地:在学习继承、多态时,很难想象实际应用场景,导致代码写得像"为了用 OOP 而用 OOP"。建议多结合游戏开发(如角色类、怪物类继承)、教务系统(如学生、老师继承自人员类)等具体案例来理解。
python
class Student:
def __init__(self, name, score):
self.name = name
self.__score = score # 私有属性,外部不能直接改
def get_level(self):
return "A" if self.__score >= 90 else "B"
def __str__(self):
return f"学生: {self.name}"
s = Student("Tom", 95)
print(s) # 输出: 学生: Tom
print(s.get_level()) # 输出: A
我的感悟: OOP 的好处不是马上能感受到的,写小项目的时候觉得"多此一举",但代码量一大就会发现,不用 OOP 根本管不过来。