使用场景:Google 的 simhash 算法

 //通过大量测试,simhash用于比较大文本,比如500字以上效果都还蛮好,距离小于3的基本都是相似,误判率也比较低。

 //从我的经验,如果我们假定N是每个块的大小,M是重叠的字符的数目,N = 4和M = 3是最好的选择

  

    public class SimHashAnalyser : IAnalyser
{ private const int HashSize = 32; public float GetLikenessValue(string needle, string haystack)
{
var needleSimHash = this.DoCalculateSimHash(needle);
var hayStackSimHash = this.DoCalculateSimHash(haystack);
return (HashSize - GetHammingDistance(needleSimHash, hayStackSimHash)) / (float)HashSize;
} private static IEnumerable<int> DoHashTokens(IEnumerable<string> tokens)
{
var hashedTokens = new List<int>();
foreach (string token in tokens)
{
hashedTokens.Add(token.GetHashCode());
}
return hashedTokens;
} private static int GetHammingDistance(int firstValue, int secondValue)
{
var hammingBits = firstValue ^ secondValue;
var hammingValue = 0;
for (int i = 0; i < 32; i++)
{
if (IsBitSet(hammingBits, i))
{
hammingValue += 1;
}
}
return hammingValue;
} private static bool IsBitSet(int b, int pos)
{
return (b & (1 << pos)) != 0;
} private int DoCalculateSimHash(string input)
{
ITokeniser tokeniser = new OverlappingStringTokeniser(4, 3);
var hashedtokens = DoHashTokens(tokeniser.Tokenise(input));
var vector = new int[HashSize];
for (var i = 0; i < HashSize; i++)
{
vector[i] = 0;
} foreach (var value in hashedtokens)
{
for (var j = 0; j < HashSize; j++)
{
if (IsBitSet(value, j))
{
vector[j] += 1;
}
else
{
vector[j] -= 1;
}
}
} var fingerprint = 0;
for (var i = 0; i < HashSize; i++)
{
if (vector[i] > 0)
{
fingerprint += 1 << i;
}
}
return fingerprint;
} } public interface IAnalyser
{
float GetLikenessValue(string needle, string haystack);
} public interface ITokeniser
{
IEnumerable<string> Tokenise(string input);
} public class FixedSizeStringTokeniser : ITokeniser
{
private readonly ushort tokensize = 5;
public FixedSizeStringTokeniser(ushort tokenSize)
{
if (tokenSize < 2 || tokenSize > 127)
{
throw new ArgumentException("Token 不能超出范围");
}
this.tokensize = tokenSize;
} public IEnumerable<string> Tokenise(string input)
{
var chunks = new List<string>();
int offset = 0;
while (offset < input.Length)
{
chunks.Add(new string(input.Skip(offset).Take(this.tokensize).ToArray()));
offset += this.tokensize;
}
return chunks;
} } public class OverlappingStringTokeniser : ITokeniser
{ private readonly ushort chunkSize = 4;
private readonly ushort overlapSize = 3; public OverlappingStringTokeniser(ushort chunkSize, ushort overlapSize)
{
if (chunkSize <= overlapSize)
{
throw new ArgumentException("Chunck 必须大于 overlap");
}
this.overlapSize = overlapSize;
this.chunkSize = chunkSize;
} public IEnumerable<string> Tokenise(string input)
{
var result = new List<string>();
int position = 0;
while (position < input.Length - this.chunkSize)
{
result.Add(input.Substring(position, this.chunkSize));
position += this.chunkSize - this.overlapSize;
}
return result;
} }

  

使用:

    const string HayStack = "中国香港………………";
const string Needle = "中国香港 2013………………"; IAnalyser analyser = new SimHashAnalyser();
var likeness = analyser.GetLikenessValue(Needle, HayStack); Console.Clear();
Console.WriteLine("Likeness: {0}%", likeness * 100);
Console.ReadKey();

  

SimHash for c#

c#-SimHash匹配相似-算法的更多相关文章

  1. 【HDU 2255】奔小康赚大钱 (最佳二分匹配KM算法)

    奔小康赚大钱 Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Subm ...

  2. HDU 5943 Kingdom of Obsession 【二分图匹配 匈牙利算法】 (2016年中国大学生程序设计竞赛(杭州))

    Kingdom of Obsession Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Oth ...

  3. USACO 4.2 The Perfect Stall(二分图匹配匈牙利算法)

    The Perfect StallHal Burch Farmer John completed his new barn just last week, complete with all the ...

  4. 浅谈压缩感知(九):正交匹配追踪算法OMP

    主要内容: OMP算法介绍 OMP的MATLAB实现 OMP中的数学知识 一.OMP算法介绍 来源:http://blog.csdn.net/scucj/article/details/7467955 ...

  5. 匹配追踪算法(MP)简介

    图像的稀疏表征 分割原始图像为若干个\[\sqrt{n} \times \sqrt{n}\]的块. 这些图像块就是样本集合中的单个样本\(y = \mathbb{R}^n\). 在固定的字典上稀疏分解 ...

  6. 全局匹配KMP算法

    KMP算法是通过分析模式字符串,预先计算每个位置发生不匹配的时候,所需GOTO的下一个比较位置,整理出来一个next数组,然后在上面的算法中使用. 本全局匹配KMP算法针对串的堆式存储数据结构 # d ...

  7. 训练指南 UVALive - 4043(二分图匹配 + KM算法)

    layout: post title: 训练指南 UVALive - 4043(二分图匹配 + KM算法) author: "luowentaoaa" catalog: true ...

  8. 二分图最大权匹配——KM算法

    前言 这东西虽然我早就学过了,但是最近才发现我以前学的是假的,心中感慨万千(雾),故作此篇. 简介 带权二分图:每条边都有权值的二分图 最大权匹配:使所选边权和最大的匹配 KM算法,全称Kuhn-Mu ...

  9. 匹配Luhn算法:可用于检测银行卡卡号

    匹配Luhn算法:可用于检测银行卡卡号 /** * http://www.cnblogs.com/JnKindle/p/5798974.html * * 匹配Luhn算法:可用于检测银行卡卡号 * * ...

随机推荐

  1. vmstat命令学习

    vmstat 是Linux/Unix系统用来进行系统监控的工具 监控的目标主要有目标服务器的cpu使用率.内存的使用情况.虚拟内存交换情况,IO读写情况. 可以通过vmstat --help来获得该命 ...

  2. word页码上加横线&&word删除单页页眉

    word(2010)页码上加横线 插入——>页脚(选择年刊型)——>如图 然后拖住“竖条条”将页码拖到正中间——>点中页脚右击——>选中“表格属性”——>“边框和底纹”— ...

  3. php遍历目录

    function zx($dir){ if(is_dir($dir)){ $filesnames = scandir($dir); foreach ($filesnames as $name) { i ...

  4. Maven 集成Tomcat插件

    转自:https://my.oschina.net/lilw/blog/168667 Maven Tomcat 插件现在主要有两个版本,tomcat-maven-plugin和tomcat7-mave ...

  5. magento事件(event)的dispatchEvent(分发)和catchEvent(获取)

    当你需要扩展Magento的核心的功能时有两个选择: (1)重写(override)Magento的core classes (2)使用Magento的event-driven 机制 由于你只能重写一 ...

  6. 用TPP开启TDD的easy模式

    Test-Drived Development 测试驱动开发三步曲:写一个失败的测试用例->编写生产代码通过这个测试用例(transformation)->重构(refactor).重构是 ...

  7. linq group by多个字段,返回多个字段.

    直接上例子.var wflist = from u in db.TWelFare where u.fy_no == fy_no orderby u.we_no group u by new { wen ...

  8. sprint3总结

    经过了半个学期以来的sprint冲刺,并且充分学习了android开发后对项目有了更加充分的认识理解,开发速度自然而然就上来了,没有了上一个学期的懵懂,虽然开发起来还是比较困难,但是胜在有同组组员帮忙 ...

  9. couldn't find setter for xxxxx

    springmvc hibernate框架,在执行普通的插入操作时报错,仔细检查实体类文件,确认该属性的getter setter方法都是有的,哭哭(´;︵;`)jpa策略生成的当然有.可是老是报这个 ...

  10. GIT-查看本地html帮助文档

    GIT安装后可以直接在命令行中通过指令调取本地html帮助文档如下所示: 格式: git help remote--git help 指令名称 git help remote 显示结果 获取branc ...