500. 反向索引

描述

创建给定文档的反向索引
确保数据不包含标点符号.

样例

给出一个包括id与内容的文档list(我们提供了document类)

[
{
"id": 1,
"content": "This is the content of document 1 it is very short"
},
{
"id": 2,
"content": "This is the content of document 2 it is very long bilabial bilabial heheh hahaha ..."
},
]
返回一个反向索引(hashmap的key是单词, value是文档的id).
{
"This": [1, 2],
"is": [1, 2],
...
}

说明
文档是有许多的单词组成的,其中每个单词也可以在同一个文档中重复出现很多次,当然,同一个单词也可以出现在不同的文档中。

  1. 正排索引(forward index):从文档角度看其中的单词,表示每个文档(用文档ID标识)都含有哪些单词,以及每个单词出现了多少次(词频)及其出现位置(相对于文档首部的偏移量)。
  2. 倒排索引(inverted index,或inverted files):从单词角度看文档,标识每个单词分别在那些文档中出现(文档ID),以及在各自的文档中每个单词分别出现了多少次(词频)及其出现位置(相对于该文档首部的偏移量)。

简单记为:正排索引:文档 ---> 单词倒排索引:单词 ---> 文档
倒排索引有着广泛的应用场景,比如搜索引擎、大规模数据库索引、文档检索、多媒体检索/信息检索领域等等。总之,倒排索引在检索领域是很重要的一种索引机制。

代码

/**
 * Definition of Document:
 * class Document {
 *     public int id;
 *     public String content;
 * }
 */
public class Solution {
    /**
     * @param docs a list of documents
     * @return an inverted index
     */
    // 正向索引是遍历文件查找关键词
    // 反向索引是通过关键词得到具有该关键词的文件 id
    public Map<String, List<Integer>> invertedIndex(List<Document> docs) {
        Map<String, List<Integer>> results = new HashMap<String, List<Integer>>();
        for (Document doc : docs) {
            int id = doc.id;
            StringBuffer temp = new StringBuffer("");
            String content = doc.content;
            int n = content.length();
            for (int i = 0; i < n; ++i) {
                // if 判断条件成立表示遍历完了一个关键词
                // temp 一次只存储一个关键词
                if (content.charAt(i) == ' ') {
                    insert(results, temp.toString(), id);
                    temp = new StringBuffer("");
                } else
                    temp.append(content.charAt(i));
            }
            // 最后一个关键词的插入
            insert(results, temp.toString(), id);
        }
        return results;
    }

    // insert 功能把关键字和 id 对应
    // tmp 即为关键字
    public void insert(Map<String, List<Integer>> rt, String tmp, int id) {
        // tmp 关键字不存在
        if (tmp.equals("") || tmp == null)
            return;
        // 建立 HashMap 
        if (!rt.containsKey(tmp))
            rt.put(tmp, new ArrayList<Integer>());
        
        int n = rt.get(tmp).size();
        // hash 表中的 id 的内容不存在或者已经存在的 id 和要添加的 id 不一致,把 id 加入 hash 表
        if (n == 0 || rt.get(tmp).get(n - 1) != id)
            rt.get(tmp).add(id);
    }
}
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • Solr&ElasticSearch原理及应用 一、综述 搜索 http://baike.baidu.com/it...
    楼外楼V阅读 7,339评论 1 17
  • 这个系列的第六个主题,主要谈一些搜索引擎相关的常见技术。 1995年是搜索引擎商业公司发展的重要起点,《浅谈推荐系...
    我偏笑_NSNirvana阅读 6,716评论 3 24
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,947评论 18 139
  • 见其名知其意,有倒排索引,对应肯定,有正向索引。正向索引(forward index),反向索引(inverted...
    时待吾阅读 1,120评论 0 0
  • 11月20天,星期一,晴 今天中午,根据预约,女儿入选了大荔"飞扬的红领巾"优秀少先队员时代影像风采展,去金色童年...
    月儿贝贝阅读 260评论 0 0