📄 matchnamerule.cs
字号:
Traffic(beforeWord, afterWord);
}
name = name + (String)preWords[index + 1];
retWords.Add(name);
return index + 2;
}
}
}
}
//统计
if (m_AutoStudy)
{
String afterWord = null;
String beforeWord = null;
if (retWords.Count > 0)
{
beforeWord = retWords[retWords.Count-1];
}
if (index + 2 < preWords.Count)
{
afterWord = preWords[index + 1];
}
Traffic(beforeWord, afterWord);
}
retWords.Add(name);
return index + 1;
}
/// <summary>
/// 匹配姓位于单词尾部的情况
/// </summary>
/// <param name="preWords"></param>
/// <param name="index"></param>
/// <param name="retWords"></param>
/// <returns></returns>
private int MatchFamilyNameInTail(List<String> preWords, int index, List<String> retWords)
{
if (retWords.Count < 1)
{
return -1;
}
String curWord = (String)retWords[retWords.Count-1];
if (curWord.Length < 2)
{
return -1;
}
String nextWord = (String)preWords[index];
if (nextWord.Length > 2)
{
return -1;
}
String familyName;
//单姓
familyName = curWord[curWord.Length - 1].ToString();
if (m_FamilyNameTbl[familyName] == null)
{
familyName = curWord.Substring(curWord.Length-2, 2);
if (m_FamilyNameTbl[familyName] == null)
{
return -1;
}
}
String remain = curWord.Substring(0, curWord.Length - familyName.Length);
if (retWords.Count > 0)
{
//重新组合前面的词,并判断词性匹配
String newWord = null;
bool isReg;
if (retWords.Count > 1)
{
newWord = retWords[retWords.Count - 2] + remain;
m_Pos.GetPos(newWord, out isReg);
if (!isReg)
{
newWord = null;
}
else
{
if (!m_PosBinRule.MatchNameInTail(newWord))
{
newWord = null;
}
}
if (newWord != null)
{
retWords.RemoveAt(retWords.Count - 1);
retWords.RemoveAt(retWords.Count - 1);
}
}
if (newWord == null)
{
newWord = remain;
m_Pos.GetPos(newWord, out isReg);
if (!isReg)
{
if (retWords.Count > 1)
{
newWord = retWords[retWords.Count - 2] + remain;
retWords.RemoveAt(retWords.Count - 1);
}
}
else
{
if (!m_PosBinRule.MatchNameInTail(newWord))
{
newWord = null;
}
}
if (newWord != null)
{
retWords.RemoveAt(retWords.Count - 1);
}
}
if (newWord != null)
{
retWords.Add(newWord);
}
else
{
return -1;
}
}
String name = familyName + nextWord;
if (name.Length - familyName.Length == 1)
{
//单字名 还要尝试是否是双字名
if (index < preWords.Count - 1)
{
String nnext = name + (String)preWords[index + 1];
nnext = nnext.Substring(familyName.Length, nnext.Length - familyName.Length);
if (nnext.Length <= 2)
{
if (!m_PosBinRule.MatchNameInHead(nnext))
{
name = name + (String)preWords[index + 1];
retWords.Add(name);
return index + 2;
}
}
}
}
retWords.Add(name);
return index + 1;
}
/// <summary>
/// 简单匹配。
/// 判断第一个单词是不是姓,如果是,
/// 如果是单字姓,再看第二个单词是不是单子,
/// 如果是,看两个词是否可以组成双字姓。
/// 不是也一样按上面逻辑判断是否是双字姓。
/// 确认姓后,看前面的单词是否是高频姓名前缀,
/// 如果是,确认为姓名,看后面的单词是否是高频
/// 姓名后缀,如果是,直接返回姓,如果不是,后面
/// 单词为两个单字,则判断第二个单字是否是高频后缀
/// 不是,合并为一个名字,是只取第一个单子。
/// 如果前面不是高频姓名前缀,判断后面如果两个字之内
/// 是否有高频姓名后缀,有则确认为姓名。
/// 确认姓名后,对前后单词加入单词前后缀,并将姓名进行
/// 记录,等到一定出现频率后,将新的姓名加入词库。
/// </summary>
/// <param name="preWords"></param>
/// <param name="index"></param>
/// <param name="retWords"></param>
/// <returns></returns>
private int SimpleMatch(List<String> preWords, int index, List<String> retWords)
{
String prefix = null;
int curIndex = index;
//获取前缀
if (retWords.Count >= 1)
{
prefix = (String)retWords[retWords.Count - 1];
}
//如果后面没有词了,则不再匹配
if (preWords.Count - index < 2)
{
return -1;
}
//第一个单词
String fstWord = (String)preWords[index];
//如果第一个单词长度大于2,通常不是中文姓氏,退出姓名匹配
if (fstWord.Length > 2)
{
return -1;
}
String famlilyName = null;
if (m_FamilyNameTbl[fstWord] == null)
{
//长度为2的单词,如果不是中文姓氏,则直接退出姓名匹配
if (fstWord.Length == 2)
{
return -1;
}
}
else
{
//此时匹配出来的姓氏如果是单字,还需要继续匹配,看是不是双字姓
famlilyName = fstWord;
}
if (fstWord.Length == 1)
{
if (preWords[index + 1].Length == 1)
{
if (m_FamilyNameTbl[fstWord + preWords[index + 1]] != null)
{
famlilyName = fstWord + preWords[index + 1];
curIndex++;
}
}
}
if (famlilyName == null)
{
return -1;
}
//通过前缀判断是否是姓名
bool isNameByPrefix = false;
//通过后缀判断是否是姓名
bool isNameByPostfix = false;
//先判断有没有姓名前缀
if (prefix != null)
{
if (m_ChsNameTraffic.MaybeNameByBefore(prefix))
{
isNameByPrefix = true;
}
}
int postfixPosition = curIndex + 1;
//如果没有前缀,又到了最后
//只有在合并双字姓氏时会发生
if (preWords.Count - curIndex < 2)
{
isNameByPostfix = false;
}
else if (preWords[postfixPosition].Length > 2)
{
//如果姓氏后面的词长度大于2,通常不是人名
isNameByPostfix = false;
}
else
{
if (m_ChsNameTraffic.MaybeNameByAfter(preWords[postfixPosition]))
{
//如果姓后面直接跟后缀,直接返回姓
isNameByPostfix = true;
}
else
{
if (preWords[postfixPosition].Length == 1)
{
//如果姓后面跟一个单字,还要判断单字后面是后缀还是单字
postfixPosition++;
if (preWords.Count - postfixPosition < 1)
{
//已经到最后
isNameByPostfix = false;
}
else if (preWords[postfixPosition][0] < 0x4e00 || preWords[postfixPosition][0] > 0x9fa5)
{
//如果后面不是汉字,则结束
isNameByPostfix = false;
}
else if (m_ChsNameTraffic.MaybeNameByAfter(preWords[postfixPosition]))
{
//是后缀
isNameByPostfix = true;
}
else
{
//不是后缀
if (preWords[postfixPosition].Length == 1)
{
//单字名后面还有一个单字,可能是双字名
postfixPosition++;
if (preWords.Count - postfixPosition < 1)
{
//已经到最后
isNameByPostfix = false;
}
else if (preWords[postfixPosition][0] < 0x4e00 || preWords[postfixPosition][0] > 0x9fa5)
{
//如果后面不是汉字,则结束
isNameByPostfix = false;
}
else if (m_ChsNameTraffic.MaybeNameByAfter(preWords[postfixPosition]))
{
//是后缀
isNameByPostfix = true;
}
else
{
//不是后缀
isNameByPostfix = false;
}
}
else
{
//单字后面跟多字,不可能合并为一个名字
isNameByPostfix = false;
}
}
}
else
{
//如果姓后面跟一个单字,还要判断单字后面是后缀还是单字
postfixPosition++;
if (preWords.Count - postfixPosition < 1)
{
//已经到最后
isNameByPostfix = false;
}
else if (preWords[postfixPosition][0] < 0x4e00 || preWords[postfixPosition][0] > 0x9fa5)
{
//如果后面不是汉字,则结束
isNameByPostfix = false;
}
else if (m_ChsNameTraffic.MaybeNameByAfter(preWords[postfixPosition]))
{
//是后缀
isNameByPostfix = true;
}
else
{
isNameByPostfix = true;
}
}
}
}
if (isNameByPostfix || isNameByPrefix)
{
//如果有前缀或后缀确认,则认为是人名
String name = famlilyName;
for (int i = curIndex + 1; i < postfixPosition; i++)
{
name += preWords[i];
}
retWords.Add(name);
if (AutoStudy)
{
if (TrafficUnknownWordHandle != null)
{
TrafficUnknownWordHandle(name, T_POS.POS_A_NR);
}
}
return postfixPosition;
}
else
{
return -1;
}
}
public int ProcRule(List<String> preWords, int index, List<String> retWords)
{
return SimpleMatch(preWords, index, retWords);
/*
int idx;
idx = MatchFamilyNameInTailByTraffic(preWords, index, retWords);
if (idx < -1)
{
return -1;
}
if (idx < 0)
{
idx = MatchFamilyNameInHead(preWords, index, retWords);
return idx;
}
else
{
return idx;
}
if (idx < -1)
{
return -1;
}
if (idx < 0)
{
return MatchFamilyNameInTail(preWords, index, retWords);
}
else
{
return idx;
}
*/
}
#endregion
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -