应使用 mb_strlen($str, 'UTF-8') 计算含 Unicode 字符、不间断空格、中文、emoji 等字符串的真实字符数,因其按 Unicode 码点计数,而 strlen() 按字节计数;需启用 mbstring 扩展,并注意 U+00A0 须用 \u{00a0} 处理。

PHP 7.0 判断含特殊字符(如 Unicode 字符、不间断空格 U+00A0、中文、emoji 等)的字符串长度,不能直接依赖 strlen(),因为它按**字节计数**,不是按“字符”计数。例如 "李四" 的 strlen() 返回 6(UTF-8 编码下每个汉字占 3 字节),但实际是 2 个字符。
用 mb_strlen() 替代 strlen() 计算真实字符数
这是最标准、最可靠的方式。需确保启用了 mbstring 扩展(PHP 默认常开启)。
-
mb_strlen($str, 'UTF-8'):明确指定 UTF-8 编码,返回 Unicode 字符个数 - 省略第二参数时,会使用
mb_internal_encoding()当前值,不推荐省略 - 示例:
mb_strlen("a\u{00a0}你好", 'UTF-8')→ 返回 5(a、NBSP、你、好,共 5 个 Unicode 码点)
特别注意不间断空格(U+00A0)的识别与处理
U+00A0 在 UTF-8 中占 2 字节(0xC2 0xA0),strlen() 会算作 2,mb_strlen() 正确识别为 1 个字符。
- 过滤它要用 Unicode 转义:
str_replace("\u{00a0}", '', $str) - 不要用
chr(160)或"\u00a0"(PHP <7.0 不支持),必须用\u{00a0}(PHP 7.0+ 支持) - 验证是否存在:
mb_strpos($str, "\u{00a0}", 0, 'UTF-8') !== false
区分“字节长”和“字符长”,按需选择函数
两者用途不同,不可混用:
立即学习“PHP免费学习笔记(深入)”;
-
strlen():适合计算内存占用、协议传输长度、二进制安全操作 -
mb_strlen():适合用户可见长度、截取显示、表单校验(如“最多 10 个汉字”) - 截取用
mb_substr($str, 0, 10, 'UTF-8'),而非substr(),否则可能截断多字节字符导致乱码
检查是否含非 ASCII 字符的快捷方式
若只需判断字符串是否“含中文/emoji/特殊符号”,可用正则或编码检测:
-
preg_match('/[\x{4e00}-\x{9fff}]/u', $str):匹配常见汉字区间 -
!ctype_ascii($str):返回 true 表示含非 ASCII 字符(简单快速) -
mb_detect_encoding($str, ['UTF-8', 'ASCII'], true) === 'UTF-8':辅助确认编码(但不保证内容全是有效 UTF-8)



















