編輯距離及編輯距離演算法
編輯距離概念描述:
編輯距離,又稱Levenshtein距離,是指兩個字串之間,由一個轉成另一個所需的最少編輯操作次數。許可的編輯操作包括將一個字元替換成另一個字元,插入一個字元,刪除一個字元。
例如將kitten一字轉成sitting:
- sitten (k→s)
- sittin (e→i)
- sitting (→g)
俄羅斯科學家Vladimir Levenshtein在1965年提出這個概念。
問題:找出字串的編輯距離,即把一個字串s1最少經過多少步操作變成程式設計字串s2,操作有三種,新增一個字元,刪除一個字元,修改一個字元
解析:
首先定義這樣一個函式——edit(i, j),它表示第一個字串的長度為i的子串到第二個字串的長度為j的子串的編輯距離。
顯然可以有如下動態規劃公式:
- if i == 0 且 j == 0,edit(i, j) = 0
- if i == 0 且 j > 0,edit(i, j) = j
- if i > 0 且j == 0,edit(i, j) = i
- if i ≥ 1 且 j ≥ 1 ,edit(i, j) == min{ edit(i-1, j) + 1, edit(i, j-1) + 1, edit(i-1, j-1) + f(i, j) },當第一個字串的第i個字元不等於第二個字串的第j個字元時,f(i, j) = 1;否則,f(i, j) = 0。
0 | f | a | i | l | i | n | g | |
0 | ||||||||
s | ||||||||
a | ||||||||
i | ||||||||
l | ||||||||
n |
0 | f | a | i | l | i | n | g | |
0 | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
s | 1 | |||||||
a | 2 | |||||||
i | 3 | |||||||
l | 4 | |||||||
n | 5 |
計算edit(1, 1),edit(0, 1) + 1 == 2,edit(1, 0) + 1 == 2,edit(0, 0) + f(1, 1) == 0 + 1 == 1,min(edit(0, 1),edit(1, 0),edit(0, 0) + f(1, 1))==1,因此edit(1, 1) == 1。 依次類推:
0 | f | a | i | l | i | n | g | |
0 | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
s | 1 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
a | 2 | 2 | ||||||
i | 3 | |||||||
l | 4 | |||||||
n | 5 |
edit(2, 1) + 1 == 3,edit(1, 2) + 1 == 3,edit(1, 1) + f(2, 2) == 1 + 0 == 1,其中s1[2] == 'a' 而 s2[1] == 'f'‘,兩者不相同,所以交換相鄰字元的操作不計入比較最小數中計算。以此計算,得出最後矩陣為:
0 | f | a | i | l | i | n | g | |
0 | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
s | 1 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
a | 2 | 2 | 1 | 2 | 3 | 4 | 5 | 6 |
i | 3 | 3 | 2 | 1 | 2 | 3 | 4 | 5 |
l | 4 | 4 | 3 | 2 | 1 | 2 | 3 | 4 |
n | 5 | 5 | 4 | 3 | 2 | 2 | 2 | 3 |
程式(C++):注意二維陣列動態分配和釋放的方法!!
#include <iostream> #include <string> using namespace std; int min(int a, int b) { return a < b ? a : b; } int edit(string str1, string str2) { int max1 = str1.size(); int max2 = str2.size(); int **ptr = new int*[max1 + 1]; for(int i = 0; i < max1 + 1 ;i++) { ptr[i] = new int[max2 + 1]; } for(int i = 0 ;i < max1 + 1 ;i++) { ptr[i][0] = i; } for(int i = 0 ;i < max2 + 1;i++) { ptr[0][i] = i; } for(int i = 1 ;i < max1 + 1 ;i++) { for(int j = 1 ;j< max2 + 1; j++) { int d; int temp = min(ptr[i-1][j] + 1, ptr[i][j-1] + 1); if(str1[i-1] == str2[j-1]) { d = 0 ; } else { d = 1 ; } ptr[i][j] = min(temp, ptr[i-1][j-1] + d); } } cout << "**************************" << endl; for(int i = 0 ;i < max1 + 1 ;i++) { for(int j = 0; j< max2 + 1; j++) { cout << ptr[i][j] << " " ; } cout << endl; } cout << "**************************" << endl; int dis = ptr[max1][max2]; for(int i = 0; i < max1 + 1; i++) { delete[] ptr[i]; ptr[i] = NULL; } delete[] ptr; ptr = NULL; return dis; } int main(void) { string str1 = "sailn"; string str2 = "failing"; int r = edit(str1, str2); cout << "the dis is : " << r << endl; return 0; }
執行效果:
轉載來自:http://www.cnblogs.com/biyeymyhjob/archive/2012/09/28/2707343.html
相關文章
- 編輯距離演算法演算法
- 最短編輯距離演算法演算法
- 計算字串編輯距離字串
- 動態規劃-編輯距離動態規劃
- 面試程式碼題(華為)編輯距離面試
- LeetCode72編輯距離LeetCode
- 字串編輯距離問題詳解字串
- Java LeetCode 72. 編輯距離JavaLeetCode
- Leetcode 編輯距離(動態規劃)LeetCode動態規劃
- 字串相似度演算法(編輯距離演算法 Levenshtein Distance)(轉)字串演算法
- 資料對齊-編輯距離演算法詳解(Levenshtein distance)演算法
- 演算法:編輯距離問題(動態規劃,詳細解答)演算法動態規劃
- 程式設計之美leetcode之編輯距離程式設計LeetCode
- 演算法——動態規劃演算法求解字串的編輯距離演算法動態規劃字串
- 【leetcode】72. Edit Distance 編輯距離計算LeetCode
- 怎樣衡量兩個字串的相似度(編輯距離動態規劃求解)字串動態規劃
- JavaScript 元素距離視窗頂部的距離JavaScript
- PostgreSQL遺傳學應用-矩陣相似距離計算(歐式距離,…XX距離)SQL矩陣
- 2014年亞馬遜線上筆試題目及解法_9_24(字串編輯距離升級版)亞馬遜筆試字串
- JavaScript獲取元素距離文件頂部的距離JavaScript
- 【動態規劃】字串最小編輯距離Java實現動態規劃字串Java
- java文字相似度計算(Levenshtein Distance演算法(中文翻譯:編輯距離演算法))----程式碼和詳解Java演算法
- Laravel 距離排序Laravel排序
- 最小距離分類器,互動式選取影像樣本分類資料,進行最小距離分類(實現歐式距離,馬氏距離,計程距離)
- javascript獲取元素距離網頁頂部的距離JavaScript網頁
- 曼哈頓距離與切比雪夫距離的互化
- 排列木樁;及模糊距離分析
- 距離度量學習
- 最長公共子序列與最小編輯距離-你有更快的演算法麼?演算法
- Martin Fowler 談“編輯”“釋出”相分離
- Vijos1680距離/openjudge2988計算字串的距離[DP]字串
- 空間距離計算
- Markdown線上、離線編輯器與使用教程
- 模糊距離;及七夕鵲橋分析
- milvus 使用 l2 歐式距離計算向量的距離,計算出來的距離的最大值是多少?
- jQuery獲取div距離視窗頂部或者父元素頂部的距離jQuery
- 28、(向量)歐幾里得距離計算
- 洛谷 1279 字串距離字串