zoukankan      html  css  js  c++  java
  • 使用boost::multi_index高速构建排行榜


    使用boost::multi_index高速构建排行榜


    前几天在boostmaillist上看到boost::multi_index将要支持ranked_index(邮件内容见附件2),这实乃我等苦逼写排行榜的人的福音。大家再也不用去分析rank_tree里的内容了,故拿出来和大家一起分享。

     

    ranked_index其内部实现和rank_tree是一样的。但其优点是集成在multi_index内部,使用上很方便,而且支持ranked_uniqueranked_non_unique两种索引。

     

    话不多说,首先从http://tinyurl.com/kemwk8q下载下来multi_index的库文件,然后替换boost_1.58中的multi_index,有一个文件夹boost/multi_index和两个文件boost/multi_index_container.hpp, boost/multi_index_container_fwd.hpp须要替换,替换之后,我们就能够把附件1里的代码拷贝到vs2008里执行啦,输出结果为:

     

    245044518

    1

    0

     

    了解过rank_tree组件的同学肯定知道是怎么回事了,ranked_indexrank_tree一样比普通的map多了两个函数。其相应关系是:

     

    ranked_index

    rank_tree

    说明

    nth

    find_by_rank

    名次到迭代器

    rank

    rank

    迭代器到名次

     

     

    附件1

    // test_rank.cpp : Defines the entry point for the console application.

    //

     

    #include "stdafx.h"

    #include <boost/multi_index_container.hpp>

    #include <boost/multi_index/member.hpp>

    #include <boost/multi_index/indexed_by.hpp>

    #include <boost/multi_index/ranked_index.hpp>

    #include <boost/multi_index/ordered_index.hpp>

    #include <iostream>

     

    namespace bmi = boost::multi_index;

     

    typedef unsigned int uint32_t;

    typedef int int32_t;

     

    struct Data

    {

        int32_t key;

        uint32_t uin;

    };

     

    struct tag_key{};

    struct tag_uin{};

     

    typedef boost::multi_index_container<

        Databmi::indexed_by<

            bmi::ranked_non_unique<

                bmi::tag<tag_key>,

                bmi::member<Dataint32_t, &Data::key>

            >,

            bmi::ordered_unique<

                bmi::tag<tag_uin>,

                bmi::member<Datauint32_t, &Data::uin>

            >

        >

    container_t;

     

    typedef container_t::index<tag_key>::type key_index_t;

    typedef container_t::index<tag_uin>::type uin_index_t;

     

    int _tmain(int argc_TCHARargv[])

    {

        container_t c;

     

        Data data;

        data.key = 200;

        data.uin = 245044518;

        c.insert(data);

     

        data.key = 100;

        data.uin = 503063727;

        c.insert(data);

     

        key_index_tkey_index = boost::get<tag_key>(c);

     

        uin_index_tuin_index = boost::get<tag_uin>(c);

     

        std::cout << key_index.nth(1)->uin << std::endl;

     

        std::cout << key_index.rank(key_index.nth(1)) << std::endl;

     

        std::cout << key_index.rank(bmi::project<tag_key>(cuin_index.find(503063727))) << std::endl;

     

             return 0;

    }

     

     

     

    附件2

    Message: 2

    Date: Wed, 22 Apr 2015 19:34:04 +0000 (UTC)

    From: Joaquin M Lopez Munoz <joaquin@tid.es>

    To: boost-users@lists.boost.org

    Subject: [Boost-users] [multi_index] Announcing preview of ranked

        indices

    Message-ID: <loom.20150422T212903-565@post.gmane.org>

    Content-Type: text/plain; charset=utf-8

     

    Hi,

     

    It's been 11 years since first proposed, but here it is at last. I'm

    releasing a prereview of ranked indices for Boost.MultiIndex:

     

      struct person

      {

        int         age;

        std::string name;

      };

     

      typedef multi_index_container<

        person,

        indexed_by<

          ranked_non_unique<member<person,int,&person::age> >,

          ordered_non_unique<member<person,std::string,&person::name>>>>

      multi_t;

     

     

      multi_t m={{40,"Joe"},{25,"Jill"},{30,"Kurt"},{32,"Sue"}};

     

      auto it=m.emplace(31,"Maggie").first;

      std::cout<<m.rank(it)<<" persons younger than "<<it->name<<" ";

     

      auto n=m.size()/2;

      std::cout<<n<<" persons are less than "<<m.nth(n)->age<<" years old ";

     

    Ranked indices add a bunch of extra rank-related capabilities to the

    interface of ordered indices. The rank of an element is its numerical

    position in the index. nth(i) returns an iterator to the element with

    rank i, whereas rank(it) is the inverse operation. Both execute in

    log(n) time.

     

    Additionally, the member functions

     

      find_rank

      lower_bound_rank

      upper_bound_rank

      equal_range_rank

      range_rank

     

    behave as their "_rank"-less counterparts except they return ranks rather

    than iterators.

     

    One drawback of ranked indices wrt ordered indices (other than their

    slower perfomance and higher memory consumption) is that deletion of

    elements is log(n) (in ordered indices it is constant time).

     

    Download lib preview: http://tinyurl.com/kemwk8q

    Tutorial: http://tinyurl.com/q36c9f7

    Reference: http://tinyurl.com/pvoulgr

     

    For people interested in this, I'd appreciate if you could download the

    source, copy it on top of Boost 1.58 (1.57 should work as well), play a bit

    with the new feature and report your results. Also, opinions on naming

    are welcome. Target version for releasing is Boost 1.59, so we have

    plenty of time to discuss the design before it is final.

     

    Thank you,

     

    Joaqu?n M L?

    pez Mu?oz

    Telef?

    nica

     

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


  • 相关阅读:
    [No0000159]C# 7 中的模范和实践
    [No0000158]思维模型1-20
    [No000014B]Office-PPT设置默认打开视图
    [No000014C]让大脑高效运转的24个技巧
    [No000014A]Linux简介与shell编程
    [No000014D]chrome console 调试 引入 jquery等外部库
    [No0000157].net core项目中拼音,excel,pdf处理库
    [No0000156]天干地支-狗年我懂,戊戌二字怎么来的?
    [No0000155]为什么32位机器最大只能用到4GB内存
    [No0000154]详解为什么32位系统只能用4G内存.
  • 原文地址:https://www.cnblogs.com/zsychanpin/p/7132034.html
Copyright © 2011-2022 走看看