PHP计算字符串编辑距离最常用Levenshtein算法,内置levenshtein()函数支持默认及自定义操作代价,手动DP实现便于扩展;实际应用需预处理、长度校验和相似度换算,similar_text()则基于字符匹配适合粗粒度检测。

PHP 中计算两个字符串编辑距离,最常用的是 Levenshtein 算法,它定义了将一个字符串转换为另一个所需的最少单字符编辑操作数(插入、删除、替换)。
使用内置 levenshtein() 函数
PHP 提供了原生函数 levenshtein(),无需手动实现,支持三种调用方式:
- 两参数形式:`levenshtein($str1, $str2)` —— 默认所有操作代价为 1;
- 五参数形式:`levenshtein($str1, $str2, $cost_insert, $cost_replace, $cost_delete)` —— 可自定义各操作代价;
- 注意:字符串长度超过 255 字节时,该函数可能返回 -1(PHP 8.0+ 已修复大部分边界问题,但仍建议预检查长度)。
手动实现动态规划版本(便于理解与定制)
当需要扩展逻辑(如支持交换相邻字符、忽略大小写、跳过空格等),可手写 DP 表。核心思路是构建二维数组 $dp[i][j] 表示 $str1[0..i-1] 与 $str2[0..j-1] 的最小编辑距离:
- 初始化:
$dp[0][j] = j(插入 j 次),$dp[i][0] = i(删除 i 次); - 状态转移:
若$str1[i-1] === $str2[j-1],则$dp[i][j] = $dp[i-1][j-1];
否则$dp[i][j] = 1 + min($dp[i-1][j], $dp[i][j-1], $dp[i-1][j-1]); - 空间优化:可用一维数组代替二维,只保留上一行结果。
实际应用中的常见处理技巧
纯数字或带格式的字符串(如电话、邮箱)直接比对编辑距离意义有限,建议预处理:
立即学习“PHP免费学习笔记(深入)”;
- 统一转小写:
strtolower(); - 移除非字母数字字符(可选):
preg_replace('/[^a-z0-9]/', '', $str); - 限制最大允许距离避免全量计算(尤其在模糊搜索中):
if (strlen($a) > 100 || strlen($b) > 100) { /* 跳过或降级处理 */ }; - 结合相似度百分比:用
(1 - $distance / max(strlen($a), strlen($b))) * 100粗略估算匹配程度(注意分母为 0 的情况)。
替代方案:相似度函数 similar_text()
PHP 还提供 similar_text(),它基于最长公共子序列思想,返回**相同字符数**而非编辑操作数:
- 用法:
similar_text($a, $b, $percent),第三个参数按引用返回相似度(0–100); - 特点:不考虑字符位置变化,对“abc”和“bca”会给出高分,而 Levenshtein 得分为 3;
- 适用场景:粗粒度内容重复检测,不适合拼写纠错或精确差异分析。











