"有志者,事竟成"--乔治-赫伯特
在试图向他人解释散列时 ,我喜欢以文章和词汇为例。
我将保持简单和直接,直奔主题。
让我们想象一下,我们有10,000个词,我们发现这些词存在于1,000篇文章中。说,像这样的东西--
如果我们假设用32个比特来代表每一个词,这将意味着整个矩阵将导致40GB的矩阵!
请注意,这里的大部分元素将是零,因为不是所有的文章都有所有的词汇。
有一种方法可以更有效地表示这些内容并减少其大小,那就是使用稀疏矩阵。
稀疏矩阵的简单做法是,以一个条目的组合为例--
并将这个组合的条目映射到哈希图上。
因此,如果我们在上面的矩阵中取i =3,j = 2,那么要映射的值将是3。
它是如何减少大小的,对于条目为0的组合,例如,i = 1000和j = 1,这个组合的映射将被跳过。
因此,我们最终实现的是一个更小的矩阵。
另一种方法,我们可以通过利用n-grams的优势来减少尺寸**。**
如果你仔细看一下上面的矩阵,你会发现我们放在矩阵中的词汇是单字,比如说 "股票 "或 "市场"。这就是1-克。
可能有用的是用组合词来代替,比如说 "股票市场"。
这就是2-grams。同样的情况还可以扩展到3格等。
因此,通过把它带到更高的词组,你最好把它的大小减少到一个更小的矩阵。
还有一种方法,也是我喜欢的方法--是的,它是 "特征散列"!我们可以放弃上述方法,而采用 "特征散列"。让我们抛开上面的内容,现在来探讨一下散列。
简单地说,特征散列所要做的是,假设我们有 "股票 "这个词。
- 我们把 "股票 "这个词放在我们称之为 "散列函数 "的地方。
- 这个哈希函数给出一个值作为输出
- 我们用我们想使用的空间对其进行修改("modulo运算符(%) "的简称)。
- 这个mod值的输出给出了一个索引i
- 我们把这个索引i映射到一个数组,然后简单地增加这个元素
感到困惑吗?请看下面的视觉效果 -
例子:我们想把大小优化到10,000个元素的价值
This would now become -
索引=4893在生成的数组中递增了1
有意义吗?
现在让我们再举一个例子。
下一个词得到一个新的索引,这个索引再次被映射到数组中
相应的索引元素被递增了1
有趣的是,如果我们得到一个哈希值相同的词,比如---------。
"update "与 "market "的哈希值相同,因此,得到相同的索引映射到数组中
索引=4912的元素被增加了1,变成了2。
因此,当碰撞发生时,我们只是继续更新
关于使用特征散列的事实 -
- 我们可以处理任意长度的文件。 这是因为只要单词不断出现,我们就可以在给定的某个(些)单词的情况下递增特定索引的值。
- 我们不需要经常为每一个新出现的词重新训练我们的整个模型,因为每次我们得到一个新的词--我们只是把它散列到一个特定的索引,并在我们的输出数组中增加相应的值。
- 对于像垃圾邮件检测这样的情况,在一个正常的文本稀疏矩阵中,对手可以很容易地掌握词汇,并使他们的电子邮件作为 "合法 "通过,干扰我们的隐私。但是,在特征散列中,对手没有任何词汇可以获得,因为我们在这里使用的是散列输出
因此,使用特征散列的好处是,你可以 将可变长度的文本文件表示为等长的数字特征向量,并实现降维。
相比之下,如果你试图将文本列原封不动地用于训练,它将被视为一个分类特征列,有很多很多不同的值。
将输出作为数字,也使得用数据使用许多不同的机器学习方法成为可能,包括分类、聚类或信息检索。因为查找操作可以使用整数哈希值而不是字符串比较,所以获得特征权重也更快。
想要更正式的阅读吗?我发现了一些关于散列和如何实现的文章--
- www.umsl.edu/~siegelj/in…(了解散列的情况)
- contrib.scikit-learn.org/category_en…(scikit-learn的分类编码库)
如果你想在LinkedIn上与我联系,请随时在这里给我发信息或请求。
当然,你也可以在这里发表你的评论!我也很乐意接受任何问题。
直到下一次,保持DSing、MLing和AIing。最重要的是,继续学习 :)
#01Don'tSkipTheseConcepts|Feature Hashing最初发表于Nerd For Techon Medium,人们通过强调和回应这个故事继续对话。