必须用 mb_substr($str, 0, N, 'UTF-8') 而非 substr(),因后者按字节截取会导致中文乱码;UTF-8 中中文占 3 字节,substr 截 5 字节可能得“你wo”,而 mb_substr 按字符计数,确保准确截取 10 个字符。

直接用 mb_substr($str, 0, N, 'UTF-8') 就行,关键是必须显式指定编码为 'UTF-8',否则中文可能被截断或计数错误。
为什么不能用 substr()
substr() 按字节操作,而一个中文在 UTF-8 中占 3 字节。比如截取前 5 个字节:"你好world" → substr($s, 0, 5) 实际拿到的是 “你”(3 字节)+ “wo”(2 字节),共 2 个中文 + 2 个英文字母,但 strlen() 却返回 5 —— 这不是你想要的“5 个字符”。
正确写法:mb_substr + 显式编码
确保按“字符”而非“字节”截取:
- 始终传入第四个参数
'UTF-8',不依赖mb_internal_encoding()的全局设置 - 示例:取前 10 个字符(含中文、英文、数字、标点都算 1 个)
$summary = mb_substr($article, 0, 10, 'UTF-8'); - 如果原文不足 10 字符,
mb_substr()自动返回全部,不会报错或补空
常见配套操作:判断是否够长再加省略号
摘要常需“至少显示 8 字,不够就加 …”:
- 用
mb_strlen($summary, 'UTF-8')测真实字符数,不是strlen() - 示例:
$summary = mb_substr($text, 0, 10, 'UTF-8');<br> if (mb_strlen($summary, 'UTF-8') $summary .= '…';<br> }
- 注意:
mb_strlen()的编码参数必须和mb_substr()一致,否则比较失效
额外提醒:PHP 7.4+ 可直接拆成字符数组
若后续还需逐字处理(如去重、统计),可用:$chars = mb_str_split($article, 1, 'UTF-8');
它比手动循环 mb_substr 更简洁安全,每个元素都是完整中文或符号,不会出现乱码字节。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











