Import Upstream version 0.03

This commit is contained in:
su-fang 2022-09-23 16:38:39 +08:00
commit 15ffdb3644
8 changed files with 265 additions and 0 deletions

13
Changes Normal file
View File

@ -0,0 +1,13 @@
Revision history for Perl extension Text::LevenshteinXS.
0.03 Tue Jun 29 14:42:00 2004
- move variable declaration to fix SGI compile error.
0.02 Sat Mar 06 10:54:00 2004
- short circuits added for special cases to increase
speed.
0.01 Wed Mar 26 10:23:49 2003
- original version; created by h2xs 1.21 with options
-n Text::LevenshteinXS

75
LevenshteinXS.pm Normal file
View File

@ -0,0 +1,75 @@
package Text::LevenshteinXS;
use strict;
use warnings;
use Carp;
require Exporter;
require DynaLoader;
use AutoLoader;
our @ISA = qw(Exporter DynaLoader);
our %EXPORT_TAGS = ( 'all' => [ qw(
) ] );
our @EXPORT_OK = ( @{ $EXPORT_TAGS{'all'} } );
our @EXPORT = qw(
distance
);
our $VERSION = '0.03';
bootstrap Text::LevenshteinXS $VERSION;
1;
__END__
=head1 NAME
Text::LevenshteinXS - An XS implementation of the Levenshtein edit distance
=head1 SYNOPSIS
use Text::LevenshteinXS qw(distance);
print distance("foo","four");
# prints "2"
print distance("foo","bar");
# prints "3"
=head1 DESCRIPTION
This module implements the Levenshtein edit distance in a XS way.
The Levenshtein edit distance is a measure of the degree of proximity between two strings.
This distance is the number of substitutions, deletions or insertions ("edits")
needed to transform one string into the other one (and vice versa).
When two strings have distance 0, they are the same.
A good point to start is: <http://www.merriampark.com/ld.htm>
=head1 CREDITS
All the credits go to Vladimir Levenshtein the author of the algorithm and to
Lorenzo Seidenari who made the C implementation <http://www.merriampark.com/ldc.htm>
=head1 SEE ALSO
Text::Levenshtein , Text::WagnerFischer , Text::Brew , String::Approx
=head1 AUTHOR
Copyright 2003 Dree Mistrut <F<dree@friul.it>>
Modifications Copyright 2004 Josh Goldberg <F<josh@3io.com>>
This package is free software and is provided "as is" without express
or implied warranty. You can redistribute it and/or modify it under
the same terms as Perl itself.
=cut

76
LevenshteinXS.xs Normal file
View File

@ -0,0 +1,76 @@
#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"
/****************************************************/
/* Levenshtein Distance Algorithm */
/* C Implementation by Lorenzo Seidenari */
/* http://www.merriampark.com/ldc.htm */
/* modified by dree */
/****************************************************/
#include <stdlib.h>
#include <string.h>
int levenshtein_distance(char *s,char*t);
int minimum(int a,int b,int c);
int levenshtein_distance(char *s,char*t)
/*Compute levenshtein distance between s and t*/
{
//Step 1
int k,i,j,n,m,cost,*d,distance;
if (strcmp(s,t) == 0) {return 0;}
n=strlen(s);
m=strlen(t);
if(n==0) {return m;}
if(m==0) {return n;}
d=malloc((sizeof(int))*(m+1)*(n+1));
m++;
n++;
//Step 2
for(k=0;k<n;k++)
d[k]=k;
for(k=0;k<m;k++)
d[k*n]=k;
//Step 3 and 4
for(i=1;i<n;i++)
for(j=1;j<m;j++)
{
//Step 5
if(s[i-1]==t[j-1])
cost=0;
else
cost=1;
//Step 6
d[j*n+i]=minimum(d[(j-1)*n+i]+1,d[j*n+i-1]+1,d[(j-1)*n+i-1]+cost);
}
distance=d[n*m-1];
free(d);
return distance;
}
int minimum(int a,int b,int c)
/*Gets the minimum of three values*/
{
int min=a;
if(b<min)
min=b;
if(c<min)
min=c;
return min;
}
MODULE = Text::LevenshteinXS PACKAGE = Text::LevenshteinXS
int
distance(s,t)
char * s
char * t
CODE:
RETVAL = levenshtein_distance(s,t);
OUTPUT:
RETVAL

8
MANIFEST Normal file
View File

@ -0,0 +1,8 @@
Changes
LevenshteinXS.pm
LevenshteinXS.xs
Makefile.PL
MANIFEST
README
test.pl
META.yml Module meta-data (added by MakeMaker)

11
META.yml Normal file
View File

@ -0,0 +1,11 @@
# http://module-build.sourceforge.net/META-spec.html
#XXXXXXX This is a prototype!!! It will change in the future!!! XXXXX#
name: Text-LevenshteinXS
version: 0.03
version_from: LevenshteinXS.pm
installdirs: site
requires:
Test:
distribution_type: module
generated_by: ExtUtils::MakeMaker version 6.17

12
Makefile.PL Normal file
View File

@ -0,0 +1,12 @@
use ExtUtils::MakeMaker;
# See lib/ExtUtils/MakeMaker.pm for details of how to influence
# the contents of the Makefile that is written.
WriteMakefile(
'NAME' => 'Text::LevenshteinXS',
'VERSION_FROM' => 'LevenshteinXS.pm',
'PREREQ_PM' => { Test },
($] >= 5.005 ? () : (
ABSTRACT_FROM => 'LevenshteinXS.pm',
AUTHOR => 'Dree Mistrut <dree@friul.it> and Josh Goldberg <josh@3io.com>'
)),
);

54
README Normal file
View File

@ -0,0 +1,54 @@
Text::LevenshteinXS is an XS implementation of the Levenshtein edit distance in Perl.
A good point to start is: <http://www.merriampark.com/ld.htm>
See also Text::Levenshtein on CPAN for a pure Perl version of this module.
PREREQUISITES
This suite requires Perl 5; I tested it only under Perl 5.6.
Text::LevenshteinXS requires the Test module.
A C compiler.
INSTALLATION
You install Text::LevenshteinXS by running these commands in the *nix environment:
perl Makefile.PL
make
make test (optional)
make install
To install Text::LevenshteinXS in the Win32 environment, use nmake instead of make.
nmake is available for free (in a self extracting executable):
<http://download.microsoft.com/download/vc15/Patch/1.52/W95/EN-US/Nmake15.exe>
After download and inflate, put nmake.exe and nmake.err in c:\windows\command .
You need also a C compiler (e.g. Visual C++).
DOCUMENTATION
POD format documentation is included in LevenshteinXS.pm.
POD is readable with the command:
perldoc Text::LevenshteinXS
AVAILABILITY
The latest version of Text::LevenshteinXS is available from the
CPAN <http://search.cpan.org/>
COPYRIGHT
Copyright 2003 Dree Mistrut <dree@friul.it>
This package is free software and is provided "as is" without express
or implied warranty. You can redistribute it and/or modify it under
the same terms as Perl itself.

16
test.pl Normal file
View File

@ -0,0 +1,16 @@
use Test;
BEGIN { plan tests => 6 };
use Text::LevenshteinXS qw(distance);
ok(1);
if (distance("foo","four") == 2) {ok(1)} else {ok(0)}
if (distance("foo","foo") == 0) {ok(1)} else {ok(0)}
if (distance("foo","") == 3) {ok(1)} else {ok(0)}
if (distance("four","foo") == 2) {ok(1)} else {ok(0)}
if (distance("foo","bar") == 3) {ok(1)} else {ok(0)}