C++实现两个字符串之间的Levenshtein Distance(编辑距离)

1.什么是Levenshtein Distance

Levenshtein Distance,又称编辑距离,指的是两个字符串之间,由一个转换成另一个所需的最少编辑操作次数。许可的编辑操作包括将一个字符替换成另一个字符,插入一个字符,删除一个字符。levenshtein() 函数返回两个字符串之间的 Levenshtein 距离。编辑距离的算法是首先由俄国科学家Levenshtein提出的,故又叫Levenshtein Distance。

2.算法

步骤 说明
1 设置n为字符串s的长度。("GUMBO") 
设置m为字符串t的长度。("GAMBOL") 
如果n等于0,返回m并退出。
如果m等于0,返回n并退出。
构造两个向量v0[m+1] 和v1[m+1],串联0..m之间所有的元素。
2 初始化 v0 to 0..m。
3 检查 s (i from 1 to n) 中的每个字符。
4 检查 t (j from 1 to m) 中的每个字符
5 如果 s[i] 等于 t[j],则编辑代价为 0;
如果 s[i] 不等于 t[j],则编辑代价为1。
6 设置单元v1[j]为下面的最小值之一:
a、紧邻该单元上方+1:v1[j-1] + 1
b、紧邻该单元左侧+1:v0[j] + 1
c、该单元对角线上方和左侧+cost:v0[j-1] + cost
7 在完成迭代 (3, 4, 5, 6) 之后,v1[m]便是编辑距离的值。

其中,cost为编辑代价,当字符相等时,为0,否则为1.

下面将演示如何计算"GUMBO"和"GAMBOL"两个字符串的Levenshtein距离

步骤1、2


v0 v1





G U M B O

0 1 2 3 4 5
G 1




A 2




M 3




B 4




O 5




L 6



 

步骤3-6,当 i = 1


v0 v1





G U M B O

0 1 2 3 4 5
G 1 0



A 2 1



M 3 2



B 4 3



O 5 4



L 6 5


 

步骤3-6,当 i = 2



v0 v1




G U M B O

0 1 2 3 4 5
G 1 0 1


A 2 1 1


M 3 2 2


B 4 3 3


O 5 4 4


L 6 5 5

 

步骤3-6,当 i = 3




v0 v1



G U M B O

0 1 2 3 4 5
G 1 0 1 2

A 2 1 1 2

M 3 2 2 1

B 4 3 3 2

O 5 4 4 3

L 6 5 5 4
 

步骤3-6,当 i = 4





v0 v1


G U M B O

0 1 2 3 4 5
G 1 0 1 2 3
A 2 1 1 2 3
M 3 2 2 1 2
B 4 3 3 2 1
O 5 4 4 3 2
L 6 5 5 4 3  

步骤3-6,当 i = 5






v0 v1


G U M B O

0 1 2 3 4 5
G 1 0 1 2 3 4
A 2 1 1 2 3 4
M 3 2 2 1 2 3
B 4 3 3 2 1 2
O 5 4 4 3 2 1
L 6 5 5 4 3 2

步骤7

编辑距离就是矩阵右下角的值,v1[m] == 2。


3.代码实现

#include 
#include 
#include 
#include 
using namespace std;

#define  min(a,b) ((a >  Tmatrix;
	Tmatrix matrix(n + 1);
	for (int i = 0; i <= n; i++)  matrix[i].resize(m + 1);

	//step 2 Initialize

	for (int i = 1; i <= n; i++) matrix[i][0] = i;
	for (int i = 1; i <= m; i++) matrix[0][i] = i;

	//step 3
	for (int i = 1; i <= n; i++)
	{
		const char si = source[i - 1];
		//step 4
		for (int j = 1; j <= m; j++)
		{

			const char dj = target[j - 1];
			//step 5
			int cost;
			if (si == dj){
				cost = 0;
			}
			else{
				cost = 1;
			}
			//step 6
			const int above = matrix[i - 1][j] + 1;
			const int left = matrix[i][j - 1] + 1;
			const int diag = matrix[i - 1][j - 1] + cost;
			matrix[i][j] = min(above, min(left, diag));

		}
	}//step7
	return matrix[n][m];
}
void main(){
	string s;
	s = "ABC";
	string d;
	d = "abcd";
	//cout << "source=";
	//cin >> s;
	//cout << "diag=";
	//cin >> d;
	int dist = ldistance(s, d);
	cout << "dist=" << dist << endl;
	system("pause");
}

参考资源:

http://www.cppblog.com/whncpp/archive/2008/09/21/62378.html

http://www.cnblogs.com/ymind/archive/2012/03/27/fast-memory-efficient-Levenshtein-algorithm.html

http://www.cnblogs.com/ac1985482/p/Levenshtein.html

http://baike.baidu.com/view/4123766.htm

http://baike.baidu.com/link?url=pz718Sg4wmsX5n7dZIBWKYDTbqUysEGiZTC48Qqj4vcJ6vcVM8E7_V927To8e7FV1Li6xLfxkyBcBM8vKxPdQRehb2OqQzcBo4uClEw_kyM3r2x4N3Lq72X00RgIY3eIW_0xq8STNBFeohe1efbdYJoDrgz3YgjtDHyqHky1zXK


你可能感兴趣的:(C++)