c#-SimHash匹配相似-算法
使用场景: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();
c#-SimHash匹配相似-算法的更多相关文章
- 【HDU 2255】奔小康赚大钱 (最佳二分匹配KM算法)
奔小康赚大钱 Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Subm ...
- HDU 5943 Kingdom of Obsession 【二分图匹配 匈牙利算法】 (2016年中国大学生程序设计竞赛(杭州))
Kingdom of Obsession Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Oth ...
- USACO 4.2 The Perfect Stall(二分图匹配匈牙利算法)
The Perfect StallHal Burch Farmer John completed his new barn just last week, complete with all the ...
- 浅谈压缩感知(九):正交匹配追踪算法OMP
主要内容: OMP算法介绍 OMP的MATLAB实现 OMP中的数学知识 一.OMP算法介绍 来源:http://blog.csdn.net/scucj/article/details/7467955 ...
- 匹配追踪算法(MP)简介
图像的稀疏表征 分割原始图像为若干个\[\sqrt{n} \times \sqrt{n}\]的块. 这些图像块就是样本集合中的单个样本\(y = \mathbb{R}^n\). 在固定的字典上稀疏分解 ...
- 全局匹配KMP算法
KMP算法是通过分析模式字符串,预先计算每个位置发生不匹配的时候,所需GOTO的下一个比较位置,整理出来一个next数组,然后在上面的算法中使用. 本全局匹配KMP算法针对串的堆式存储数据结构 # d ...
- 训练指南 UVALive - 4043(二分图匹配 + KM算法)
layout: post title: 训练指南 UVALive - 4043(二分图匹配 + KM算法) author: "luowentaoaa" catalog: true ...
- 二分图最大权匹配——KM算法
前言 这东西虽然我早就学过了,但是最近才发现我以前学的是假的,心中感慨万千(雾),故作此篇. 简介 带权二分图:每条边都有权值的二分图 最大权匹配:使所选边权和最大的匹配 KM算法,全称Kuhn-Mu ...
- 匹配Luhn算法:可用于检测银行卡卡号
匹配Luhn算法:可用于检测银行卡卡号 /** * http://www.cnblogs.com/JnKindle/p/5798974.html * * 匹配Luhn算法:可用于检测银行卡卡号 * * ...
随机推荐
- java读取xml文件
public ArrayList getMessage(){ String xmlFileName = null; List list = new ArrayList(); MessageBean m ...
- <五>JDBC_利用反射及JDBC元数据编写通用的查询方法
此类针对javaBean类写了一个通用的查询方法,List<javaBean> 通用查询更新中...:通过学习,深刻体会到学会反射就等于掌握了java基础的半壁江山! 一.使用JDBC驱动 ...
- c语言完成宽带拨号
学校的网络每次开机都需要手动登陆,于是用c写了一个自动登陆的小程序... 程序功能超级简单...只是懒得每次都登陆... PS:代码功能具体没有测试...我自己用的是python #include & ...
- “神马”框架之LigerUI
我曾经参与一个产品的研发,前端框架用的就是LigerUI,之前我也没有听过这个框架. 因为是项目期初设计就定下来用LigerUI,根据系统的功能前端页面有跟多丰富的表现,所以需要改进前端效果,这次发现 ...
- 不小心删除了sysWOW64下的webio.dll
weibo的桌面客户端留了一个服务,在syswow64目录下留了个exe文件,看着旁边好像还有个weibo.dll,就把试着也删除了,但是删除不掉,我就进安全模式删除了(f8在Windows的启动界面 ...
- Mac&iOS之多线程--转自http://geeklu.com/2012/02/thread/
http://geeklu.com/2012/02/thread/ 首先循环体的开始需要检测是否有需要处理的事件,如果有则去处理,如果没有则进入睡眠以节省CPU时间. 所以重点便是这个需要处理的事件, ...
- asp.net identity 3.0.0 在MVC下的基本使用 序言
本人也尚在学习使用之中,错误之处请大家指正. 开发环境:vs2015 UP1 项目环境:asp.net 4.6.1 模板为:asp.net 5 模板 identity版本为:asp.n ...
- js无刷新上传文件
传统的文件上传方式 <form action="" method="POST" enctype="multipart/form-data&quo ...
- Redis 3.2 Linux 环境集群搭建与java操作
redis 采用 redis-3.2.4 版本. 安装过程 1. 下载并解压 cd /usr/local wget http://download.redis.io/releases/redis-3. ...
- mysql 联合查询后update
SELECT a.user_name,a.avatar,a.nicheng,a.user_rank,b.rank_name,b.rank_img FROM ecs_users a , ecs_user ...