【发布时间】:2012-07-17 03:34:55
【问题描述】:
我正在尝试根据 2 个字符串之间的比较来分配相似度分数。 R中是否有相同的功能。我知道SAS中有一个名为SPEDIS的功能。请告诉我R中是否有这样的功能。
【问题讨论】:
-
你探索过
adist和agrep吗?我不熟悉 SPEDIS。
标签: r string-comparison edit-distance
我正在尝试根据 2 个字符串之间的比较来分配相似度分数。 R中是否有相同的功能。我知道SAS中有一个名为SPEDIS的功能。请告诉我R中是否有这样的功能。
【问题讨论】:
adist和agrep吗?我不熟悉 SPEDIS。
标签: r string-comparison edit-distance
函数adist 计算两个字符串之间的Levenshtein edit distance。这可以转化为相似性度量 1 - (Levenshtein 编辑距离/更长的字符串长度)。
RecordLinkage 包中的levenshteinSim 函数也直接执行此操作,并且可能比adist 更快。
library(RecordLinkage)
> levenshteinSim("apple", "apple")
[1] 1
> levenshteinSim("apple", "aaple")
[1] 0.8
> levenshteinSim("apple", "appled")
[1] 0.8333333
> levenshteinSim("appl", "apple")
[1] 0.8
ETA:有趣的是,虽然 RecordLinkage 包中的 levenshteinDist 似乎比 adist 稍快,但 levenshteinSim 比两者都慢得多。使用rbenchmark 包:
> benchmark(levenshteinDist("applesauce", "aaplesauce"), replications=100000)
test replications elapsed relative
1 levenshteinDist("applesauce", "aaplesauce") 100000 4.012 1
user.self sys.self user.child sys.child
1 3.583 0.452 0 0
> benchmark(adist("applesauce", "aaplesauce"), replications=100000)
test replications elapsed relative user.self
1 adist("applesauce", "aaplesauce") 100000 4.277 1 3.707
sys.self user.child sys.child
1 0.461 0 0
> benchmark(levenshteinSim("applesauce", "aaplesauce"), replications=100000)
test replications elapsed relative
1 levenshteinSim("applesauce", "aaplesauce") 100000 7.206 1
user.self sys.self user.child sys.child
1 6.49 0.743 0 0
这种开销仅仅是因为levenshteinSim 的代码,它只是levenshteinDist 的包装:
> levenshteinSim
function (str1, str2)
{
return(1 - (levenshteinDist(str1, str2)/pmax(nchar(str1),
nchar(str2))))
}
仅供参考:如果您总是比较两个字符串而不是向量,您可以创建一个使用 max 而不是 pmax 的新版本,并将运行时间缩短约 25%:
mylevsim = function (str1, str2)
{
return(1 - (levenshteinDist(str1, str2)/max(nchar(str1),
nchar(str2))))
}
> benchmark(mylevsim("applesauce", "aaplesauce"), replications=100000)
test replications elapsed relative user.self
1 mylevsim("applesauce", "aaplesauce") 100000 5.608 1 4.987
sys.self user.child sys.child
1 0.627 0 0
长话短说 - adist 和 levenshteinDist 在性能方面几乎没有区别,但如果您不想添加包依赖项,则前者更可取。如何将其转化为相似性度量确实会对性能产生一些影响。
【讨论】: