单词拼写检查器 C++实现

前几天在微博上看到了谷歌某位写的一篇博客,如何写一个小巧的单词拼写检查器:http://norvig.com/spell-correct.html

由于英语水平的限制,以及不了解python,所以这边文章不敢保证和原文的思想完全一致。

我对原文的一些细节的地方,做了细微的修改(尽量不影响效果)。最大的一处修改为编辑距离,原文计算了编辑距离为2的所有单词,而这儿我只计算了距离为1的单词。(可以对我的代码稍作修改从而达到距离为2的单词:递归调用Enum函数)


不扯了,上干货---

用户输入一个单词w,返回一个正确的单词c(有可能为w),使得这种c(输入w的情况下)尽可能合理。

原理主要是贝叶斯概率公式,可以参见原文,这儿直接给出算法。

1.如果用户输入的w存在我们的语料库中,即可认为w是一个正确的单词(语料库的限制,不100%正确),故直接返回w;

2.如果w不存在语料库中,对w作距离为1的编辑,该编辑过程如下:

---删除。 每次删除w中的一个字符,于是我们得到若干个单词. 如abc, 我们可以得到bc,ac,ab三个新的单词,他们与原单词距离为1

---交换。依次交换每相邻的两个字符,如abc,我们可以得到bac acb。

---增加。每次增加一个新的字符(从a到z)如abc,我们可以得到多个单词,不一一列举:aabc,babc,cabc......aabc,abbc.......

---修改。对每个原单词的字符,用abc去替代原字符。 如abc, 我们可以得到,不一一列举:bbc,cbc,zbc......abd,abk,abz....

3.通过步骤2,我们得到若干个编辑距离为1的单词,对这些单词,统计在语料库中出现的次数,哪个单词出现次数最多,则返回该单词给用户。


注,原文统计了距离为2的单词,可以在上面第二部后得出的单词,递归调用Enum函数(需做小修改),从而得到距离为2的单词。

完整工程文件:http://download.csdn.net/detail/owen_kop/5272516

(工程文件有一行代码有问题,请用下面的代码直接覆盖)

可以在vs2010下直接编译运行,包含语料库(model.txt)

截图


源码:

#include "stdafx.h"
typedef struct node
{
	string correctWord;
	int count;
}correction;
void TrainModel();
void Enum(string input);
void Judge(string s);
correction c;
map dic;
int _tmain(int argc, _TCHAR* argv[])
{
	cout<<"wanna quit,click x\n";
	cout<<"training model, it may take one or two minutes\n";
	TrainModel();
	string input;
	while(true)
	{
		cout<<"input:";
		c.count=-1;
		cin>>input;
		if(dic.count(input)>0)
			cout<<"correct!"<>s)
	{
		string temp(s);
		if(dic.count(temp)==0)
		{
			dic[temp]=1;
		}
		else
		{
			int count=dic.at(temp);
			dic[temp]=(count+1);
		}
	}
}

void Enum(string input)
{
	char set[27]="abcdefghijklmnopqrstuvwxyz";
	int length=input.length();
	// delete
	for(int i=0;ic.count)
	{
		c.count=number;
		c.correctWord=s;
	}
}


你可能感兴趣的:(算法)