SymSpellPlusPlus 中的分词
WordSegmentation in SymSpellPlusPlus
我想使用C++版本的SymSpell,它被称为SymSpellPlusPlus。在 C# 版本中,使用 WordSegmentation 如下所示(从第一个链接):
//word segmentation and correction for multi-word input strings with/without spaces
inputTerm="thequickbrownfoxjumpsoverthelazydog";
maxEditDistance = 0;
suggestion = symSpell.WordSegmentation(input);
//display term and edit distance
Console.WriteLine(suggestion.correctedString + " " + suggestion.distanceSum.ToString("N0"));
在C++版本中,分词返回共享指针(从第二个链接):
...
shared_ptr<WordSegmentationItem> WordSegmentation(const char* input)
{
return WordSegmentation(input, this->maxDictionaryEditDistance, this->maxDictionaryWordLength);
}
shared_ptr<WordSegmentationItem> WordSegmentation(const char* input, size_t maxEditDistance)
{
return WordSegmentation(input, maxEditDistance, this->maxDictionaryWordLength);
}
shared_ptr<WordSegmentationItem> WordSegmentation(const char* input, size_t maxEditDistance, size_t maxSegmentationWordLength)
{
// lines 1039 - 1179 under second link
std::vector<shared_ptr<WordSegmentationItem>> compositions;
...
return compositions[circularIndex];
}
在我的代码中,我尝试了以下代码:
const char* inputTerm = "whereis th elove hehad dated forImuch of thepast who couqdn'tread in sixtgrade and ins pired him";
auto suggestions = symSpell.WordSegmentation(inputTerm);
但它给出了一个错误:
free() invalid next size (fast)
它与内存错误有关,但我不知道如何克服这个问题。
类分词项如下所示(第二个链接中的第 292-325 行):
class WordSegmentationItem
{
public:
const char* segmentedString{ nullptr };
const char* correctedString{ nullptr };
u_int8_t distanceSum = 0;
double probabilityLogSum = 0;
WordSegmentationItem() { }
WordSegmentationItem(const symspell::WordSegmentationItem & p)
{
this->segmentedString = p.segmentedString;
this->correctedString = p.correctedString;
this->distanceSum = p.distanceSum;
this->probabilityLogSum = p.probabilityLogSum;
}
WordSegmentationItem& operator=(const WordSegmentationItem&) { return *this; }
WordSegmentationItem& operator=(WordSegmentationItem&&) { return *this; }
void set(const char* pSegmentedString, const char* pCorrectedString, u_int8_t pDistanceSum, double pProbabilityLogSum)
{
this->segmentedString = pSegmentedString;
this->correctedString = pCorrectedString;
this->distanceSum = pDistanceSum;
this->probabilityLogSum = pProbabilityLogSum;
}
~WordSegmentationItem()
{
delete[] segmentedString;
delete[] correctedString;
}
};
我应该如何从 WordSegmentationItem 获取更正的字符串?
该库有问题,作者需要进行一些修复。
首先,编译给了我们一个关于SuggestItem::ShallowCopy
的警告,它通过引用返回一个局部变量。很差!我们可能可以将其更改为按值返回。
但是,这并不能解决崩溃问题。
如果我们克隆库的存储库,则在调试器中运行以下测试用例:
#include "symspell6.h"
int main()
{
const char* inputTerm = "whereis th elove hehad dated forlmuch of thepast who couqdn'tread in sixtgrade and ins pired him";
symspell::SymSpell symSpell;
auto suggestions = symSpell.WordSegmentation(inputTerm);
}
...我们看到从WordSegmentation
函数返回compositions[circularIndex]
会导致shared_ptr
构造函数中的访问无效。这表明circularIndex
是越界的,给了我们一个不存在的shared_ptr
。的确,circularIndex
是95
,但compositions.size()
是0
!
该函数缺少一些严重的错误检查。
现在,只有作者(或者至少知道库应该做什么的人;那不是我!)才能正确解决这个问题。但作为一个快速补丁,我在第 1055 行之后添加了以下内容:
if (compositions.empty())
return nullptr;
...它现在至少可以运行了。
该函数似乎假定字典为非空。我不知道这是否是预期的行为(除了上面详述的缺失错误检查)。
该项目非常需要一些文档,因为没有提到这些功能的前置条件或后置条件,也没有说明应该如何使用库。同样,作者应该解决这些问题。
- 是默认情况下分配给char数组常量的值
- 当我尝试使用 sstream 和分面将 Boost Time_duration转换为字符串时,我没有得到所需的格式
- 在C++中将变量 wstring 分配给 Char 数组
- 内存错误低于在C++年实现埃拉托色尼筛分时的预期
- 为什么我能够为阵列分配比计算机实际拥有的内存更多的内存
- 如何将内联匿名函数分配给C++函数指针
- SymSpellPlusPlus 中的分词
- 使用 C++ 的字符串到分词符
- Qt等效于提升分词器表达式/构造
- 使用 BOOST 分词器显示分隔符,并且不对引号中的字符串进行分词
- 使用 ICU 进行分词
- C++数学分词器/解析器错误
- 访问增强分词器的元素
- 提升分词器以将带引号的字符串视为一个标记
- 当我的分词器识别出令牌时,如何执行其他操作
- 分词器 - 预期聚合对象使用"{...}"进行初始化
- C++ 分词器变量中的错误'std::stringstream mystream'具有初始值设定项但类型不完整
- 错误的分词
- 分词错误-比较不同的单词在c++输入中出现的次数
- OpenCV 3.0分词故障(视觉词袋)