返回专题首页

Python 专题

掌握基础数据类型:数字、字符串、布尔值与 None

学习任何一门语言,最先接触的都是数据类型。Python 在这部分看起来很直观,但真正写起代码来,数字计算、字符串处理、真值判断以及 `None` 的语义,仍然是最容易积累误解的地方。

Python 专题第 04 篇 / 39 篇9 分钟

学习任何一门语言,最先接触的都是数据类型。Python 在这部分看起来很直观,但真正写起代码来,数字计算、字符串处理、真值判断以及 None 的语义,仍然是最容易积累误解的地方。

这一节我们会重新梳理这些最基础的成员,不只是记住“有哪些类型”,更重要的是理解它们在表达、转换和判断中的行为差异,为后面的容器、函数和控制流打好底子。

数字类型:int、float 与 complex

在 Python 里,数字相关的基础类型主要有三类:

  • int:整数;
  • float:浮点数;
  • complex:复数。

前两者最常见,第三种在大部分日常业务项目里并不会高频出现,但知道它的存在有助于建立更完整的认知。

很多初学者会把“数字类型”理解成只是拿来做加减乘除,这当然没错,但数字真正容易出问题的地方,往往在于不同数字类型之间的行为差异。

比如说,整数和浮点数都能参与运算,但它们在结果表现上并不总是一致:

print(1 + 2)      # 3
print(1 + 2.0)    # 3.0
print(5 / 2)      # 2.5
print(5 // 2)     # 2
print(5 % 2)      # 1

这里有几个需要尽早形成习惯的点:

  • 只要运算里混入了浮点数,结果通常也会偏向浮点数;
  • / 表示常规除法,结果通常是浮点数;
  • // 表示整除,更接近“去掉小数部分”后的结果;
  • % 表示取余,在循环、分页、奇偶判断中都很常见。

再进一步,浮点数还有一个经典问题:精度误差。比如:

print(0.1 + 0.2)  # 结果并不总是你以为的 0.3

这不是 Python 的特殊问题,而是计算机里二进制浮点表示的普遍现象。所以,一个很重要的意识是:浮点数适合大多数普通计算,但不适合直接承担高精度金额等场景的精确比较。

至于 complex,你可以把它理解为 Python 提供的复数支持能力:

z = 1 + 2j

它在数学计算、信号处理等场景里才会更常见。对当前这套专题来说,你不需要深入它的使用,只要知道 Python 的数字系统并不止整数和浮点数两种即可。

所以,在数字类型这一部分,真正重要的不只是记住名字,而是理解:

  • 整数和浮点数会在运算中互相影响结果类型;
  • /// 不是一回事;
  • 浮点数有精度边界;
  • 数值类型的差异会直接影响后面你写出的判断和业务逻辑。

字符串:定义、拼接与格式化

如果说数字更多承担“计算”的职责,那么字符串承担的就是“表达”和“组织信息”的职责。日志、提示信息、用户名、路径、配置、JSON 字段、SQL 片段,几乎处处都离不开字符串。

Python 中的字符串非常容易上手,可以使用单引号、双引号来定义:

name = 'Colin'
lang = "Python"

如果你需要多行文本,也可以使用三引号:

message = """
Hello
Python
"""

字符串本身是不可变类型。这一点非常重要。它的意思不是“字符串不能被重新赋值”,而是“你不能在原地修改字符串内部某个字符”。很多字符串处理方法,本质上都是返回一个新的字符串,而不是修改原始值。

比如:

text = "python"
upper_text = text.upper()
print(text)        # python
print(upper_text)  # PYTHON

在组织字符串时,最基础的方式当然是拼接:

name = "Colin"
print("Hello, " + name)

但只要稍微复杂一点,单纯用 + 拼接就会开始变得笨重,因此格式化能力就显得非常关键。

f-string 为什么成为主流

Python 里最推荐的字符串格式化方式,通常就是 f-string:

name = "Colin"
score = 95
print(f"{name} got {score} points")

它之所以成为主流,核心原因其实很直接:可读性好、写起来顺手、表达力强。

和更早期的 % 格式化、str.format() 相比,f-string 的优势主要在于:

  • 模板和变量放在一起,阅读负担更低;
  • 写法更短;
  • 可以自然嵌入表达式。

比如:

count = 3
print(f"double count = {count * 2}")

在真实项目里,只要是 Python 3.6+ 环境,绝大多数日常字符串格式化场景都优先推荐 f-string。

当然,这并不意味着你要完全忘掉其他写法,只是要知道:如果没有特殊兼容性要求,f-string 通常就是第一选择。

常见字符串处理方法

字符串处理之所以高频,是因为大量输入、输出、清洗、拼接动作最后都会落到字符串上。这里不需要一口气记住所有方法,但有一批高频操作非常值得尽早熟悉:

  • strip():去掉首尾空白;
  • lower() / upper():统一大小写;
  • replace():替换内容;
  • split():按规则拆分;
  • join():把多个字符串连接起来;
  • startswith() / endswith():判断前后缀。

例如:

text = "  Hello,Python  "
print(text.strip())
print(text.lower())
print(text.replace("Python", "World"))
print("a,b,c".split(","))
print("-".join(["2026", "04", "10"]))

这些方法背后有一个共同点:它们几乎都返回一个新字符串。这也再次印证了前面那句话,字符串是不可变的。

当你后面开始写接口、日志、文件处理甚至爬虫时,这些方法会出现得非常频繁。所以这一部分最好的学习方式不是背诵,而是多写几次,慢慢形成手感。

布尔值与条件判断

布尔值本身只有两个成员:

  • True
  • False

它们看起来很简单,但真正值得注意的,是 Python 对“真假”的判断规则并不只局限于显式的布尔值。

例如:

print(bool(0))        # False
print(bool(1))        # True
print(bool(""))       # False
print(bool("hi"))     # True
print(bool([]))       # False
print(bool([1]))      # True
print(bool(None))     # False

这说明 Python 存在一套真值判断规则:很多对象在条件判断里都会被自动解释成真或假,而不必先手动转成 True / False

最常见的“假值”通常包括:

  • 0
  • 0.0
  • 空字符串 ""
  • 空列表 []
  • 空字典 {}
  • 空集合 set()
  • None

这也是为什么你经常会看到这样的写法:

items = []
if not items:
    print("empty")

这种写法没有问题,也很 Pythonic。但与此同时,你也要知道一个风险:“值为空”和“值不存在”并不是一回事。

比如空字符串 ""None 在条件判断里都可能表现为假,但它们的语义完全不同。一个表示“确实有值,只是为空”,另一个更接近“当前没有值”。

因此,布尔判断真正重要的不是记住 TrueFalse,而是开始区分:

  • 我是在判断真假;
  • 还是在判断是否为空;
  • 还是在判断是否为 None

只要这三件事不混,后面的条件分支就会稳定很多。

None 的意义与常见误用

None 在 Python 里非常高频,但也非常容易被误用。很多初学者会把它简单理解成“空值”,这并不完全错,但还不够准确。

更贴近的理解应该是:None 表示当前没有值、没有结果,或者某个位置暂时不指向任何有效对象。

它常见于这些场景:

  • 函数没有显式返回值时,默认返回 None
  • 某个变量当前还没有真正数据;
  • 某个查询、查找或配置读取结果不存在。

例如:

def greet():
    print("hello")

result = greet()
print(result)  # None

很多人第一次看到这个现象会有点意外,但它其实非常重要:没有显式 return 的函数,不是“什么都没有”,而是返回 None

与此同时,None 还有一个很关键的使用习惯,就是判断时优先使用 is

value = None
if value is None:
    print("no value")

为什么不推荐写成 value == None?因为 None 更像一个单独的特殊对象,使用 is 来判断身份通常更清晰,也更符合 Python 社区习惯。

None 最常见的误用,通常有两个:

1. 把 None 和空字符串、空列表、0 混为一谈;2. 在本该返回明确数据结构的地方,随手返回 None,导致调用方不得不到处额外判断。

所以,学 None 的重点不只是知道它存在,而是学会问清楚:这里到底是“没有值”,还是“有值但为空”?

类型查看与基本转换

当你开始同时处理数字、字符串、布尔值和 None 时,类型查看与转换就会变得非常常见。

在 Python 里,最直接的类型查看方式是:

value = 123
print(type(value))

这能帮助你快速确认一个变量当前是什么类型,尤其是在学习阶段、调试阶段很有帮助。

而基本类型转换,则通常依赖这些内置函数:

  • int()
  • float()
  • str()
  • bool()

比如:

print(int("12"))
print(float("3.14"))
print(str(100))
print(bool(""))

但这里一定要建立一个意识:类型转换不是永远安全的。

例如:

int("hello")   # 会报错
float("abc")   # 会报错

也就是说,转换函数并不是魔法,它只能在输入本身满足转换规则时正常工作。因此,后面只要输入来自用户、文件、接口或数据库,就要开始有“转换失败怎么办”的意识,这和异常处理会直接连起来。

另外,还有一个值得尽早记住的点:不要为了“看起来统一”而过度转换类型。如果一个值本来就应该是数字,那就尽量让它保持数字;如果一个值承担的是展示职责,那再把它转成字符串。类型转换应该服务于场景,而不是成为习惯性动作。

总结与预告

这一节我们重新梳理了 Python 最基础的数据类型,并重点理解了它们在转换、判断和表达中的差异。基础类型看起来简单,但它们几乎参与了后面所有语法和工程实践。

下一节我们会继续往上走一步,把这些基础值装进更常用的容器结构里,看看列表、元组、字典和集合分别适合解决什么问题。