NLTK 中具有非对称填充的 Ngram

Ngrams with non-symmetrical padding in NLTK

单词 TEXT 的四元语法是

>>generated_ngrams = ngrams('TEXT', 4, pad_left=True, pad_right=True, left_pad_symbol=' ', right_pad_symbol=' ')

>>list(generated_ngrams)
[(' ', ' ', ' ', 'T'), (' ', ' ', 'T', 'E'), (' ', 'T', 'E', 'X'), ('T', 'E', 'X', 'T'), ('E', 'X', 'T', ' '), ('X', 'T', ' ', ' '), ('T', ' ', ' ', ' ')]

根据我的说法,输出应该是 _TEX, TEXT, EXT__, XT__。 根据这个网站 (http://cloudmark.github.io/Language-Detection/) 输出是 _TEX, TEXT, EXT_, XT__, T___
它还继续说 "In general a string of length k, padded with blanks, will have k+1 bi-grams, k+1 tri-grams, k+1 quad-grams and so on."
根据我从 Python 获得的输出,我认为这是无效的。
请解释一下。

填充确保实际字符串的每个符号都出现在 ngram 的所有位置。因此,对于 4-grams,将有最后一个符号的三个填充 ngrams,E X T _X T _ _T _ _ _ 等,如您的代码所示。

您link要访问的网站在左侧添加一个space,然后在右侧适当填充。这就是计数不同的原因。这为所有长度提供了相同数量的 ngram。这是对应的Python代码:

generated_ngrams = ngrams(" " + 'TEXT', 4, 
                          pad_left=False, pad_right=True, right_pad_symbol=' ')

为什么会这样,只有博主自己知道。但是在右边而不是左边填充的一个结果是,正如博客指出的那样,给定长度 k 的字符串将产生固定数量的 n-grams (k+1) n-gram 大小 n。首字母 space 对此没有贡献,但用作单词边界符号:以 space 开头的 ngram 是单词首字母。

@alexis answer 将为您提供单字符左垫和多字符右垫。

如果我们仔细阅读博文:

We will also append blanks to the beginning and end of strings in order to help with matching the beginning-of-word and end-of-word situations.

We will represent this using the _ character. Given the word TEXT we would obtain the following N-Grams:

bi-grams _T, TE, EX, XT, T_
tri-grams _TE, TEX, EXT, XT_, T__
quad-grams _TEX, TEXT, EXT_, XT__, T___

非对称填充的动机尚不清楚。

继续博文:

In general a string of length k , padded with blanks, will have k+1 bi-grams, k+1 tri-grams, k+1 quad-grams and so on.

从NLTK实现和对称填充来看,应该是:

A specifically, a string of length k symmetrical padding with blanks will yield k + (n-1) ngrams. For the case where the word is TEXT:

>>> from functools import partial
>>> from nltk import ngrams
>>> padded_ngrams = partial(ngrams, pad_left=True, pad_right=True, left_pad_symbol='_', right_pad_symbol='_')
>>> x = 'TEXT'

>>> list(ngrams(x, 2))
[('T', 'E'), ('E', 'X'), ('X', 'T')]
>>> len(list(ngrams(x, 2)))
3

>>> list(padded_ngrams(x, 2))
[('_', 'T'), ('T', 'E'), ('E', 'X'), ('X', 'T'), ('T', '_')]
>>> len(list(padded_ngrams(x, 2)))
5
>>> len(list(padded_ngrams(x, 3)))
6
>>> len(list(padded_ngrams(x, 4)))
7
>>> len(list(padded_ngrams(x, 5)))
8

争论对称填充与非对称填充,这是一种使用数据集进行测试并查看特征在分类任务中的影响的原则性方法。