[转](2条消息) Elasticsearch全文搜索与TF/IDF

转载:https://my.oschina.net/stanleysun/blog/1594220

一、TF/IDF

1. TF

TF:Term Frequency,即词频。它表示一个词在内容(如某文章)中出现的次数。为了消除文档本身大小的影响,通常,它的定义是:

TF = 某个词在文档中出现的次数 / 文档的总词数

也有其他表示方法,在Elasticsearch (lucene)中的使用的方法是

tf(t in d) = √frequency  , 即 (某个词t在文档d中出现的次数) 的 平方跟

某个词出现越多,表示它约重要。比如某篇新闻中,“剑术”出现了5次,“电视”出现了1次,很可能这是一个剑术赛事报道。

如果这篇新闻中,“中国”和“剑术”出现的次数一样多,是不是表示两者同等重要呢?答案是否定的,因为中国这个词很常见,它难以表达文档的特性。而剑术很少见,更能表达文章的特性。

某个词越少见,就越能表达一篇文章的特性,反之则越不能。像“的”、“了”这些词,在所有文档中出现的频率都特别高,以至于失去了表达文章特性的意义。人们干脆称它们为“停用词”,直接从统计中忽略掉。

 

2. IDF

IDF(Inverse Document Frequency),即逆文档频率,它是一个表达词语重要性的指标。通常,它的计算方法是:

IDF=log(语料库中的文档数/(包含该词的文档数+1))

如果所有文章都包涵某个词,那个词的IDF=log(1)=0, 即重要性为零。停用词的IDF约等于0。

如果某个词只在很少的文章中出现,则IDF很大,其重要性也越高。

为了避免分母为0,所以+1.

在Elasticsearch (lucene)中的计算方法是

idf(t) = 1 + log ( numDocs / (docFreq + 1)) ,

即 1 + log ( 索引中的文档总数 / (包含该词的文档数 + 1))

上述公式是文档中给的,但实际中用的是 log(1 + (docCount - docFreq + 0.5) / (docFreq + 0.5)) 

 

TF-IDF值

TF-IDF = TF X IDF

 

在Elasticsearch中,还有一个概念叫 字段长度的归一化,Field-Length Norm.

字段内容越短,权重越大。如果一个关键词出现在较短的字段中,比如title,就比它出现在长字段(如简介)中更能表达文章的特性。

norm(d) = 1 / √numTerms    即: 1 / 词出现次数的平方根

 

二、elasticsearch的全文搜索

 

elasticsearh的全文搜索涉及到两个重要的方面:相关性(Relevance)和分析(Analysis)

相关性(Relevance)

它是评价查询与其结果间的相关程度,并根据这种相关程度对结果排名的一种能力,这种计算方式可以是 TF/IDF 方法(参见 相关性的介绍)、地理位置邻近、模糊相似,或其他的某些算法。本文只介绍TF/IDF方法。

 

TF/IDF 相关性方法分析

做一次搜索,带explain,elasticsearch会返回如何匹配。比如在title字段中进行全文搜索,关键词为'python'

 
  1. GET course/_search?explain
  2. {
  3. "query": {
  4. "multi_match" : {
  5. "query": "python",
  6. "fields": [ "title" ]
  7. }
  8. },"size":10
  9. }

返回内容中,第一条匹配的结果如下

 
  1. {
  2. "_shard": "[course][0]",
  3. ...
  4. "_score": 6.1884723,
  5. "_source": {
  6. "title": "Python 语句",
  7. ...
  8. },
  9. "_explanation": {
  10. "value": 6.1884723,
  11. "description": "weight(title:python in 1363) [PerFieldSimilarity], result of:",
  12. "details": [
  13. {
  14. "value": 6.1884723,
  15. "description": "score(doc=1363,freq=1.0 = termFreq=1.0\n), product of:",
  16. "details": [
  17. {
  18. "value": 4.4812255,
  19. "description": "idf, computed as log(1 + (docCount - docFreq + 0.5) / (docFreq + 0.5)) from:",
  20. "details": [
  21. {
  22. "value": 17,
  23. "description": "docFreq",
  24. "details": []
  25. },
  26. {
  27. "value": 1545,
  28. "description": "docCount",
  29. "details": []
  30. }
  31. ]
  32. },
  33. {
  34. "value": 1.3809776,
  35. "description": "tfNorm, computed as (freq * (k1 + 1)) / (freq + k1 * (1 - b + b * fieldLength / avgFieldLength)) from:",
  36. "details": [
  37. {
  38. "value": 1,
  39. "description": "termFreq=1.0",
  40. "details": []
  41. },
  42. {
  43. "value": 1.2,
  44. "description": "parameter k1",
  45. "details": []
  46. },
  47. {
  48. "value": 0.75,
  49. "description": "parameter b",
  50. "details": []
  51. },
  52. {
  53. "value": 7.861489,
  54. "description": "avgFieldLength",
  55. "details": []
  56. },
  57. {
  58. "value": 2.56,
  59. "description": "fieldLength",
  60. "details": []
  61. }
  62. ]
  63. }
  64. ]
  65. }
  66. ]
  67. }
  68. }

 

解释

 
  1. "value": 4.4812255,
  2. "description": "idf, computed as log(1 + (docCount - docFreq + 0.5) / (docFreq + 0.5)) from:",

上面是求idf值的值。idf=ln(1 + (docCount - docFreq + 0.5) / (docFreq + 0.5))=ln(1+(1545-17+0.5)/(17+0.5)) = ln(88.34)=4.4812255

//返回内容里用了log(以10为底的对数), 实际是ln (以e为底的对数)

 
  1. "value": 1.3809776,
  2. "description": "tfNorm, computed as (freq * (k1 + 1)) / (freq + k1 * (1 - b + b * fieldLength / avgFieldLength)) from:",

上面是求tfNorm(归一化后的TF)的值。根据描述tfNorm = (freq * (k1 + 1)) / (freq + k1 * (1 - b + b * fieldLength / avgFieldLength))

其中termFreq=1,k1=1.2, b=0.75, avgFieldLength=7.861489, fieldLength=2.56。

为什么要用这样的公式,以及k1和b的值是怎么来的,我也不清楚。

计算最终结果,tfNorm=1.38.

 
  1. "value": 6.1884723,
  2. "description": "score(doc=1363,freq=1.0 = termFreq=1.0\n), product of:",

最终得分 TF-IDF = TF * IDF =4.4812255 * 1.3809776 = 6.1884723

---------------------------------------------------------------------

扩展阅读:http://www.cnblogs.com/biyeymyhjob/archive/2012/07/17/2595249.html

 


---------------------
作者:a flying bird
来源:CSDN
原文:https://blog.csdn.net/m0_37870649/article/details/81123506
版权声明:本文为作者原创文章,转载请附上博文链接!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值