strcmp() 严格按 ascii 字节比较,strcasecmp() 先转小写再字节比较,二者均不支持 utf-8;判断 utf-8 字符串相等应使用 ===,排序需用 collator 类。

strcmp() 和 strcasecmp() 的区别在哪
PHP 字符串比较不是看“字典序大小”就完事,而是分大小写敏感和不敏感两种逻辑。strcmp() 严格按 ASCII 值逐字节比,strcasecmp() 先转小写再比,但两者都只适用于单字节编码(如 ASCII、ISO-8859-1)。遇到中文、emoji 或 UTF-8 多字节字符时,结果不可靠——比如 strcmp("你好", "hello") 返回负数,但这不代表“你好”比 "hello" 小,只是首字节 0xE4 和 0x68 的数值比较而已。
- 用
strcmp()判断相等?可以,但仅限纯 ASCII 场景;strcasecmp()同理,别拿它比中文 - 想安全判断两个 UTF-8 字符串是否相等?直接用
===(注意是全等,不是==) - 需要真正按 Unicode 排序规则比较大小?必须上
Collator类,不是函数能解决的
为什么 == 和 === 在字符串比较中行为不同
== 会触发类型转换,而字符串比较时最常踩的坑就是数字字符串被悄悄转成整数。比如 "123" == 123 返回 true,但 "0123" == 123 也返回 true(因为 "0123" 被当成了八进制?不,PHP 实际是先转 float 再比,细节很绕),这种隐式转换让结果难以预测。
-
===是唯一推荐用于字符串相等判断的操作符:不转类型、不忽略前导空格、不忽略末尾空格 -
==在字符串场景下基本没正当用途,除非你明确要模拟表单提交后数字字符串与整数混用的旧逻辑 - 空字符串
""、"0"、0、false用==两两比较可能全为true,但用===只有相同类型+值才成立
多字节字符串(UTF-8)怎么安全比较大小
PHP 原生函数对 UTF-8 支持有限:strcmp() 拆的是字节,不是字符;mb_strtolower() + strcmp() 组合看似可行,但大小写转换本身就有语言依赖(比如土耳其语的 i/I 规则),而且排序顺序 ≠ 简单转小写再比。
- 真正需要按用户预期排序(比如中文按拼音、德语按变音符号规则)?必须用
Collator类:$coll = new Collator('zh_CN');<br>var_dump($coll->compare("苹果", "香蕉")); -
mb_strcmp()并不存在——别搜这个函数名,它是常见误解 - 如果只是想判断是否相等且兼容 UTF-8,
===依然够用;但凡涉及“哪个在前/哪个更大”,就得跳出原生函数思维
性能差异大吗:函数 vs 操作符 vs 扩展类
单纯判断相等,=== 是 C 层直接内存比较,最快;strcmp() 多一次函数调用开销,但差距微乎其微;而 Collator::compare() 要加载 ICU 库、解析区域设置、处理 Unicode 归一化,慢一个数量级很正常。
立即学习“PHP免费学习笔记(深入)”;
- 线上高频判断字符串是否相等?无条件选
=== - 做搜索关键词高亮前的匹配?
stripos()比先strtolower()再strpos()更省事也更快 - 用
Collator前确认:你的 PHP 编译时带了--with-icu-dir,且extension=icu.so已启用,否则运行时报Class 'Collator' not found











