题目链接:
https://wenku.baidu.com/view/d8253e24f90f76c660371ac2.html?from=search
问题描述:
某些文件编辑器提供纠正英文单词拼写错误的功能。你们本次要解决的问题就是实现这样一个能够完成自动纠正拼写错误( ACM)功能的应用程序。
ACM能够纠正以下几类的单词拼写错误:
1.漏写或多写1个字母,例如单词“letter”被写成了“leter”,或者是“letter”被写成了“ ltter”。
2.写错了一个字母,例如“letter”被写成了“ketter”。
3.两个相邻的字母书写顺序弄错了,例如“letter” 被写成了“ lettre”。
ACM的纠错功能是基于-一个已知单词集的字典来进行的。每当-一个文档中含有字典中不存在的单词时,ACM就会试图用字典中与该单词最相似的单词替代它。ACM对单词是相似的有这样的定义:只要两个单词能够按照上面叙述的3类拼写错误规则中的任何一种进行相互转换,就认为这两个单词是相似的。如果在字典中没有发现相似的单词,就在原文本中保留这个未知的单词。
输入:
在输入文件的第1行里将给出字典中己知的单词数量:整数n,其中0<=n<=1000。在紧接着的n行里包含有字典中的n个单词。在这n行后的第1行里将给出1个正整数q,其中0<=q<= 1000,它表示需要查询单词的数量。在这之后的q行里包含有q个需要查询的单词。你可以假设在输入文件中每-一个单词只能由26个小写字母(‘a’~‘z’) 构成。
输出:
针对每一-个需要查询的单词,输出一-行字符串。要求:该字符串以需要查询的单词开始,并从下面3个黑体描述中选择一个合适的字串添加在后。
1.如果需要查询的单词在字典中就添加字串“is correct’
2.如果需要查询的单词不在字典中,则添加字串“is a misspelling of 其中是指字典与需要查询的单词相似的单词。若x有多个,则选择在字典中出现最早的那个单词输出。
3.如果前面两种情况都不满足,则添加字串“is unknown”。
输入样本:
10
this
is
a
dictionary
that
we
will
use
for
us
6
su
as
the
dictionary
us
willl
输出样本:
su is a misspelling of us
as is a misspelling of is
the is unknown
dictonary is a misspelling of dictionary
us is correct
willl is a misspelling of will
思路==================================================================
注意:这里题目【输入样本】的【dictionary】应该是【dictonary】
这道题跟之前有道【翻译】的题目思路差不多都是逐个单词对比,但这里多了个【相似】规则,而判断相似的关键在于目标字词的差异个数;
条件分析:
1.漏写或多写1个字母,例如单词“letter”被写成了“leter”,或者是“letter”被写成了“ ltter”。
单词长度差=1,差异个数=1;
2.写错了一个字母,例如“letter”被写成了“ketter”。
单词长度差=0,差异个数=2
3.两个相邻的字母书写顺序弄错了,例如“letter” 被写成了“ lettre”。
单词长度差=0,差异个数=2
然后就是怎么找相似部分,具体分类我添加到输入中(稍微改了下题目)
List<string> readLineStrings = new List<string> {// 方便测试
"11",
"this",
"is",
"en",
"a",
"dictionary",
"that",
"we",
"will",
"use",
"for",
"us",
"26",
"su",
"as",
"the",
"us",
"willl",
"dictionary",// 正确
"ictionary",// 前端漏一个
"dictonary",// 中间漏一个
"dictionar",// 后端漏一个
"Xdictionary",// 前端多一个
"dictiXonary",// 中间多一个
"dictionaryX",// 后端多一个
"Xictionary",// 前端错一个
"dictXonary",// 中间错一个
"dictionarX",// 后端错一个
"idctionary",// 前端顺序错一个
"dictoinary",// 中间顺序错一个
"dictionayr",// 后端顺序错一个
"en",// 正确
"n",// 前端漏一个
"e",// 后端漏一个
"qen",// 前端多一个
"enq",// 后端多一个
"pn",// 前端错一个
"ep",// 后端错一个
"ne",// 顺序错
};
int n1 = int.Parse( readLineStrings[0]);
List<string> dictionaryList = new List<string>(readLineStrings.GetRange(1,n1));// 字典
dictionaryList.ForEach((dic)=> { dic.ToLower(); });
int n2 = int.Parse(readLineStrings[n1+1]);
List<string> writeList = new List<string>(readLineStrings.GetRange(n1 + 1+1, n2));// 测试单词
writeList.ForEach((word) => { word.ToLower(); });
foreach (string str in writeList)
{
bool isLike = false;// 是否存在或存在相似(存在题意所述的3种情况)
foreach (string word in dictionaryList)
{
if (word == str)
{
isLike = true;
Console.WriteLine(str + " is correct");
break;
}
else if (!dictionaryList.Contains(str))
{
int lengthDiff = word.Length - str.Length;// 字典值与测试单词长度差
if (lengthDiff == 1) // 1.1.漏写,例如单词“letter”被写成了“leter”
{
for (int i = 0; i <= str.Length; i++)
{
if ((word.StartsWith(str.Substring(0, i)) && word.EndsWith(str.Substring(i, str.Length - i))))
{
isLike = true;
Console.WriteLine(str + " is a misspelling(1.1) of " + word);
break;
}
}
}
else if (lengthDiff == -1)// 1.2.多写1个字母,例如单词“letter”被写成了“lettter”。
{
for (int i = 0; i <= str.Length - 1; i++)
{
if (word.StartsWith(str.Substring(0, i)) && word.EndsWith(str.Substring(i + 1, str.Length - (i + 1))))
{
isLike = true;
Console.WriteLine(str + " is a misspelling(1.2) of " + word);
break;
}
}
}
else if (lengthDiff == 0)
{
for (int i = 0; i <= str.Length - 1; i++)// 2.写错了一个字母,例如“letter”被写成了“ketter”。
{
if ((word.StartsWith(str.Substring(0, i)) && word.EndsWith(str.Substring(i + 1, str.Length - (i + 1)))))
{
isLike = true;
Console.WriteLine(str + " is a misspelling(2) of " + word);
break;
}
}
for (int i = 0; i <= str.Length - 2; i++)
{
if (word == (str.Substring(0, i) + str[i + 1] + str[i] + str.Substring(i + 2, str.Length - (i + 2)))) // 3.两个相邻的字母书写顺序弄错了,例如“letter” 被写成了“ lettre”。
{
isLike = true;
Console.WriteLine(str + " is a misspelling(3) of " + word);
break;
}
}
}
}
if (isLike) break;
}
if (!isLike)
{
Console.WriteLine(str + " is unknown");
}
}
Console.ReadKey();