机器学习:找到最接近查询向量的结果
Posted
技术标签:
【中文标题】机器学习:找到最接近查询向量的结果【英文标题】:Machine learning : find the closest results to a queried vector 【发布时间】:2016-01-01 06:06:55 【问题描述】:我有数千个向量,每个向量大约有 20 个特征。
给定一个查询向量和一组潜在匹配项,我希望能够选择最佳的 N
匹配项。
我花了几天时间尝试回归(使用 SVM),用我自己创建的数据集训练我的模型:每个向量都是查询向量和结果向量的串联,我给出一个分数(主观评价)介于 0 和 1 之间,0 表示完美匹配,1 表示最差匹配。
我没有取得很好的成绩,我相信一个原因可能是很难主观地分配这些分数。另一方面,更容易对结果进行主观排名(score
是一个未知函数):
score(query, resultA) > score(query, resultB) > score(query, resultC)
所以我相信这更多是Learning to rank 的问题,我找到了 Python 的各种链接:
http://fa.bianp.net/blog/2012/learning-to-rank-with-scikit-learn-the-pairwise-transform/ https://gist.github.com/agramfort/2071994 ...但我一直无法理解它是如何工作的。我真的对所有术语感到困惑,成对排名等等......(请注意,我对机器学习一无所知,因此我感觉有点迷茫)等等......所以我不知道不明白如何将此应用于我的问题。
有人能帮我澄清一下吗,指出我要解决的问题的确切类别,以及如何在 Python (scikit-learn) 中更好地实现这一点?
【问题讨论】:
看起来你想要一种无监督的学习方法。查看最近的邻居scikit-learn.org/stable/modules/neighbors.html 如果我错了,请纠正我,但我相信如果我想使用最近的邻居,我需要能够订购我的整个数据集......这是我做不到的。就我而言,结果的顺序取决于查询。 这可能最好在交叉验证时问:stats.stackexchange.com @CharlieHaley 是的,您可能是对的……尽管显然对于机器学习问题的归属没有明确的共识。我会请版主来移动它。 @sebpiq 对数据集进行排序是不正确的。您需要的是数据中每个样本与数据中每个其他样本之间的距离(欧几里得、闵可夫斯基等)。在欧几里得的情况下,这只是两个向量之间的距离;对于一个简单的场景,考虑笛卡尔平面上 [0, 0] 和 [5, 5] 之间的距离。如果您从 N X M 矩阵开始,您的距离矩阵也将是 N X M。然后,如果您有兴趣找到与任意样本最近的邻居,您只需在距离矩阵中查找最小值的索引。 【参考方案1】:在我看来,您要做的只是简单地计算查询与其余数据之间的距离,然后将最接近的 N 个向量返回给您的查询。这是一个搜索问题。 没有排序,您只需测量查询与“数千个向量”之间的距离。最后,您对距离进行排序并取最小的 N 值。这些对应于与您的查询最相似的 N 个向量。
为了提高比较效率,您可以使用 KD-Trees 或其他高效的搜索结构:http://scikit-learn.org/stable/modules/neighbors.html#kd-tree
然后,查看 Lp 空间上的 Wikipedia 页面。在选择合适的指标之前,您需要考虑数据及其表示:
-
您正在处理什么样的数据?它来自哪里,它代表什么?特征空间是仅由实数组成还是包含二进制值、分类值或全部?用于同质数据与异构数据的 Wiki。
对于实值特征空间,欧几里得距离 (L2) 通常是使用的选择度量,有 20 个特征应该没问题。从这个开始。否则,您可能需要考虑城市街区距离 (L1) 或其他指标,例如 Pearson 相关性、余弦距离等。 您可能必须先对数据进行一些工程,然后才能执行其他任何操作。
-
功能是否在同一尺度上?例如x1 = [0,1], x2 = [0, 100]
如果没有,请尝试扩展您的功能。这通常是一个反复试验的问题,因为某些功能可能很嘈杂,在这种情况下缩放可能无济于事。 为了解释这一点,请考虑一个具有两个特征的数据集:身高和体重。如果高度以厘米 (10^3) 为单位,重量以公斤 (10^1) 为单位,那么您应该将厘米转换为米,这样两个特征的重量相等。对于具有广泛值的特征空间,这通常是一个好主意,这意味着您对这两个特征都有大量的值样本。理想情况下,您希望所有特征都呈正态分布,只有一点噪音 - 请参阅中心极限定理。
-
所有功能都相关吗?
如果您使用的是真实有价值的数据,您可以使用主成分分析 (PCA) 对特征进行排名并仅保留相关的特征。 否则可以尝试特征选择http://scikit-learn.org/stable/modules/classes.html#module-sklearn.feature_selection 减小空间的尺寸会提高性能,尽管在您的情况下这并不重要。
如果您的数据由连续、分类和二进制值组成,则旨在对数据进行缩放或标准化。使用您对数据的了解来提出适当的表示。这是大部分工作,或多或少是一种黑色艺术。反复试验。
附带说明一下,基于度量的方法(例如 knn 和 kmeans)只是存储数据。学习从记忆结束的地方开始。
【讨论】:
谢谢!这些都是好点... 1) 我的特征都是实数 2) 我已经使用scikit-learn.org/stable/modules/preprocessing.html 标准化了我的数据 3) 尤其如此。我已经开始仔细研究我的特征,确实有很多垃圾。我会清理它,看看我是否能得到更好的结果。可悲的是没有神奇的公式可以让这一切快速轻松地工作:) 那么你很幸运。我会尝试标准化(z 分数)和缩放 [0,1]。另一个技巧是使向量单位长度(将每个向量除以其 L2 或 L1 范数)。 如果您想研究其他降维方法,请查看自动编码器,即 pca 的非线性版本。您可能还想研究度量学习。祝你好运,玩得开心! 谢谢!我做了很多清理工作,我将特征数量除以 2。我认为它开始起作用了......以上是关于机器学习:找到最接近查询向量的结果的主要内容,如果未能解决你的问题,请参考以下文章