Professional Documents
Culture Documents
The purpose of this short essay is to describe the Levenshtein distance algorithm and show how it can be
implemented in three different programming languages.
Levenshtein distance (LD) is a measure of the similarity between two strings, which we will refer to as the
source string (s) and the target string (t). The distance is the number of deletions, insertions, or substitutions
required to transform s into t. For example,
If s is "test" and t is "test", then LD(s,t) = 0, because no transformations are needed. The strings are
already identical.
If s is "test" and t is "tent", then LD(s,t) = 1, because one substitution (change "s" to "n") is sufficient to
transform s into t.
The greater the Levenshtein distance, the more different the strings are.
Levenshtein distance is named after the Russian scientist Vladimir Levenshtein, who devised the algorithm in
1965. If you can't spell or pronounce Levenshtein, the metric is also sometimes called edit distance.
Spell checking
Speech recognition
DNA analysis
Plagiarism detection
The following simple Java applet allows you to experiment with different strings and compute their
Levenshtein distance:
1 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
Steps
Step Description
1 Set n to be the length of s.
Set m to be the length of t.
If n = 0, return m and exit.
If m = 0, return n and exit.
Construct a matrix containing 0..m rows and 0..n columns.
2 Initialize the first row to 0..n.
Initialize the first column to 0..m.
3 Examine each character of s (i from 1 to n).
4 Examine each character of t (j from 1 to m).
5 If s[i] equals t[j], the cost is 0.
If s[i] doesn't equal t[j], the cost is 1.
6 Set cell d[i,j] of the matrix equal to the minimum of:
a. The cell immediately above plus 1: d[i-1,j] + 1.
b. The cell immediately to the left plus 1: d[i,j-1] + 1.
c. The cell diagonally above and to the left plus the cost: d[i-1,j-1] + cost.
7 After the iteration steps (3, 4, 5, 6) are complete, the distance is found in cell d[n,m].
Example
This section shows how the Levenshtein distance is computed when the source string is "GUMBO" and the
target string is "GAMBOL".
Steps 1 and 2
GUMBO
01 2 3 4 5
G 1
A 2
M3
B 4
2 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
O 5
L 6
Steps 3 to 6 When i = 1
GUMBO
01 2 3 4 5
G 10
A 21
M32
B 43
O 54
L 65
Steps 3 to 6 When i = 2
GUMBO
01 2 3 4 5
G 10 1
A 21 1
M32 2
B 43 3
O 54 4
L 65 5
Steps 3 to 6 When i = 3
GUMBO
01 2 3 4 5
G 10 1 2
A 21 1 2
M32 2 1
B 43 3 2
O 54 4 3
L 65 5 4
Steps 3 to 6 When i = 4
GUMBO
3 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
01 2 3 4 5
G 10 1 2 3
A 21 1 2 3
M32 2 1 2
B 43 3 2 1
O 54 4 3 2
L 65 5 4 3
Steps 3 to 6 When i = 5
GUMBO
01 2 3 4 5
G 10 1 2 3 4
A 21 1 2 3 4
M32 2 1 2 3
B 43 3 2 1 2
O 54 4 3 2 1
L 65 5 4 3 2
Step 7
The distance is in the lower right hand corner of the matrix, i.e. 2. This corresponds to our intuitive realization
that "GUMBO" can be transformed into "GAMBOL" by substituting "A" for "U" and adding "L" (one
substitution and 1 insertion = 2 changes).
Religious wars often flare up whenever engineers discuss differences between programming languages. A
typical assertion is Allen Holub's claim in a JavaWorld article (July 1999): "Visual Basic, for example, isn't in
the least bit object-oriented. Neither is Microsoft Foundation Classes (MFC) or most of the other Microsoft
technology that claims to be object-oriented."
A salvo from a different direction is Simson Garfinkels's article in Salon (Jan. 8, 2001) entitled "Java: Slow,
ugly and irrelevant", which opens with the unequivocal words "I hate Java".
We prefer to take a neutral stance in these religious wars. As a practical matter, if a problem can be solved in
one programming language, you can usually solve it in another as well. A good programmer is able to move
from one language to another with relative ease, and learning a completely new language should not present
any major difficulties, either. A programming language is a means to an end, not an end in itself.
As a modest illustration of this principle of neutrality, we present source code which implements the
Levenshtein distance algorithm in the following programming languages:
4 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
Java
C++
Visual Basic
Java
public class Distance {
//****************************
// Get minimum of three values
//****************************
mi = a;
if (b < mi) {
mi = b;
}
if (c < mi) {
mi = c;
}
return mi;
//*****************************
// Compute Levenshtein distance
//*****************************
// Step 1
n = s.length ();
m = t.length ();
if (n == 0) {
return m;
}
if (m == 0) {
return n;
}
d = new int[n+1][m+1];
// Step 2
5 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
d[0][j] = j;
}
// Step 3
// Step 4
// Step 5
if (s_i == t_j) {
cost = 0;
}
else {
cost = 1;
}
// Step 6
// Step 7
return d[n][m];
C++
In C++, the size of an array must be a constant, and this code fragment causes an error at compile time:
int sz = 5;
int arr[sz];
This limitation makes the following C++ code slightly more complicated than it would be if the matrix could
simply be declared as a two-dimensional array, with a size determined at run-time.
6 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
int GetAt (int *pOrigin, int col, int row, int nCols);
void PutAt (int *pOrigin, int col, int row, int nCols, int x);
};
#include "distance.h"
#include <string.h>
#include <malloc.h>
//****************************
// Get minimum of three values
//****************************
mi = a;
if (b < mi) {
mi = b;
}
if (c < mi) {
mi = c;
}
return mi;
//**************************************************
// Get a pointer to the specified cell of the matrix
//**************************************************
int *Distance::GetCellPointer (int *pOrigin, int col, int row, int nCols)
{
return pOrigin + col + (row * (nCols + 1));
}
//*****************************************************
// Get the contents of the specified cell in the matrix
//*****************************************************
int Distance::GetAt (int *pOrigin, int col, int row, int nCols)
{
int *pCell;
//*******************************************************
// Fill the specified cell in the matrix with the value x
//*******************************************************
void Distance::PutAt (int *pOrigin, int col, int row, int nCols, int x)
{
int *pCell;
7 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
//*****************************
// Compute Levenshtein distance
//*****************************
// Step 1
n = strlen (s);
m = strlen (t);
if (n == 0) {
return m;
}
if (m == 0) {
return n;
}
sz = (n+1) * (m+1) * sizeof (int);
d = (int *) malloc (sz);
// Step 2
// Step 3
s_i = s[i-1];
// Step 4
t_j = t[j-1];
// Step 5
if (s_i == t_j) {
cost = 0;
8 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
}
else {
cost = 1;
}
// Step 6
// Step 7
Visual Basic
'*******************************
'*** Get minimum of three values
'*******************************
mi = a
If b < mi Then
mi = b
End If
If c < mi Then
mi = c
End If
Minimum = mi
End Function
'********************************
'*** Compute Levenshtein Distance
'********************************
' Step 1
9 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
n = Len(s)
m = Len(t)
If n = 0 Then
LD = m
Exit Function
End If
If m = 0 Then
LD = n
Exit Function
End If
ReDim d(0 To n, 0 To m) As Integer
' Step 2
For i = 0 To n
d(i, 0) = i
Next i
For j = 0 To m
d(0, j) = j
Next j
' Step 3
For i = 1 To n
s_i = Mid$(s, i, 1)
' Step 4
For j = 1 To m
t_j = Mid$(t, j, 1)
' Step 5
' Step 6
Next j
Next i
' Step 7
LD = d(n, m)
Erase d
End Function
10 of 11 1/20/2016 10:17 AM
Levenshtein Distance http://people.cs.pitt.edu/~kirk/cs1501/Pruhs/Fall2006/Assignments/editdi...
The following people have kindly consented to make their implementations of the Levenshtein Distance
Algorithm in various languages available here:
11 of 11 1/20/2016 10:17 AM