2013-03-13 154 views
6

我需要删除带有许多段落的文本中的重复段落。如何比较两段文字?

我使用类java.security.MessageDigest中的函数来计算每个段落的MD5哈希值,然后将这些哈希值添加到Set中。

如果add()'ed成功,则表示最新的段落是重复的。

有没有这种方式的风险?

String.equals()之外,有没有其他方法可以做到这一点?

+0

我认为这是一个更好的方法,而不是做字符串比较。 – 2013-03-13 10:15:10

+0

我同意拉文德拉。 MD5不会产生独特的哈希。 – 2013-03-13 10:15:55

+0

他们需要匹配_exactly_还是忽略前导/尾随空格? – 2013-03-13 10:19:03

回答

0

我认为这是一个好方法。然而,有一些事情要记住:

  1. 请注意,计算哈希是一个沉重的操作。如果你不得不重复数百万段落,这可能导致你的程序变慢。
  2. 即使以这种方式,您最终可能会得到稍微不同的段落(例如打字错误,例如),从而导致未检测到。如果是这种情况,则应在计算散列之前对其段落进行规格化(将其置于小写,删除额外空格等等)。
1

如果MD5散列尚未在集合中,则表示段落是唯一的。但事实恰恰相反。所以如果你发现哈希已经在集合中,你可以用潜在地具有一个非重复的哈希值。这是不太可能的,但你必须对所有其他人测试该段落,以确保。为此String.equals会做。另外,你应该很好地考虑你所说的独特(关于错字,空格,首都等等),但任何方法都是如此。

1

没有必要计算MD5散列,只需使用HashSet并尝试将字符串本身放入该集合。这将使用String#hashCode()方法来计算字符串的散列值并检查它是否已经在集合中。使用LinkedHashSet甚至保持段落的原始顺序。

1

正如其他人所建议的,您应该意识到标点符号,空格,换行符等的细微差别可能会导致您的哈希因段落基本相同而不同。也许你应该考虑一个不太脆弱的指标,比如说。 Cosine Similarity这非常适合用于匹配段落。

欢呼声,

2

散列之前,你可以正常化段落例如,删除标点符号,转换为小写字母并删除额外的空格。 标准化后,只有不同的段落才会得到相同的散列。