gpt4 book ai didi

boost - 查找 boost multi index 标签到索引和索引数量

转载 作者:行者123 更新时间:2023-12-02 09:13:39 24 4
gpt4 key购买 nike

我有一个模板类(CrMultiIndex),它接收 boost 多索引(GlobalHash)的定义作为模板参数。

我需要:

  1. 根据使用的索引向我的模板类添加统计信息。所以我需要一种方法在初始化时使用现有索引的数量调整向量(m_StatsByIndex)的大小。
  2. 我仍然希望用户根据标签而不是索引号进行搜索。所以我需要一种从标签转换为索引号的方法,这样我就可以根据向量中的索引更新向量中的统计信息。

我有模板类

template <typename KeysType, typename MultiIndexType>
class CrMultiIndex
{

std::vector<SrStatisticsByIndex> m_StatsByIndex;

public:
MultiIndexType *m_pMultiIndex=NULL;

CrMultiIndex()
{
m_pMultiIndex = new MultiIndexType(typename
MultiIndexType::ctor_args_list());
}

以下是boost多索引容器的定义:

typedef boost::multi_index::multi_index_container<
CrUsersKeys,
UsersKey_hash_indices/*,
bip::allocator<CrUsersKeys,bip::managed_shared_memory::segment_manager>*/
> GlobalHash;

具有根据Tag搜索功能

template <typename TagType,typename SearchingKey>
typename MultiIndexType::template index<TagType>::type::iterator
GetIteratorBy(SearchingKey & key)
{
return m_pMultiIndex->template get<TagType>().find(key) ;
}

代码位于 http://coliru.stacked-crooked.com/a/d97195a6e4bb7ad4

最佳答案

您需要查询嵌入的索引类型列表:

typedef typename MultiIndexType::index_type_list::size NumberOfIndexes;

template <typename Tag> constexpr static size_t IndexOfTag() {
namespace mpl = boost::mpl;
using tl = typename MultiIndexType::index_type_list;
using B = typename mpl::begin<tl>::type;
using helper = typename MultiIndexType::template index<Tag>;
static_assert(helper::index_found, "index not found");
auto N = mpl::distance<B, typename helper::iter>::value;
return N;
}

或者,一直使用 Boost Mpl:

typedef typename MultiIndexType::index_type_list::size NumberOfIndexes;

template <typename Tag> constexpr static size_t IndexOfTag() {
namespace mpl = boost::mpl;
using tl = typename MultiIndexType::index_type_list;
using B = typename mpl::begin<tl>::type;
using E = typename mpl::end<tl>::type;
using It = typename mpl::find_if<tl, bmi::detail::has_tag<Tag> >::type;
static_assert(not std::is_same<E, It>(), "index not found");
auto N = mpl::distance<B, It>::value;
return N;
}

你可以像这样使用它:

template <typename TagType, typename SearchingKey>
typename MultiIndexType::template index<TagType>::type::iterator
GetIteratorBy(SearchingKey &key) {
auto& idx = m_pMultiIndex.template get<TagType>();
auto& stats = GetStats<TagType>();

auto it = idx.find(key);
++(it == idx.end()? stats.searchedNotFound : stats.searchedSuccessfully);

return it;
}

演示

请注意,代码已被简化:

Live On Coliru

#include <iostream>
#include <boost/multi_index/member.hpp> // for member
#include <boost/multi_index/hashed_index.hpp> // for hashed_unique
#include <boost/multi_index/ordered_index.hpp> // for ordered_non_unique
#include <boost/multi_index_container.hpp> // for multi_index_container

namespace bmi = boost::multi_index;

struct SrStatisticsByIndex {
int deleted;
int searchedSuccessfully;
int searchedNotFound;
};

template <typename MultiIndexType, typename ValueType = typename MultiIndexType::value_type>
class CrMultiIndex {

typedef typename MultiIndexType::index_type_list::size NumberOfIndexes;

template <typename Tag> constexpr static size_t IndexOfTag() {
using tl = typename MultiIndexType::index_type_list;
using B = typename boost::mpl::begin<tl>::type;
using helper = typename MultiIndexType::template index<Tag>;
static_assert(helper::index_found, "index not found");

return boost::mpl::distance<B, typename helper::iter>::value;
}

public:
MultiIndexType m_pMultiIndex;

template <typename Tag> SrStatisticsByIndex& GetStats()
{ return m_StatsByIndex.at(IndexOfTag<Tag>()); }

template <typename Tag> SrStatisticsByIndex const& GetStats() const
{ return m_StatsByIndex.at(IndexOfTag<Tag>()); }

// All the protected function are non locking function
template <typename TagType, typename SearchingKey>
typename MultiIndexType::template index<TagType>::type::iterator
GetIteratorBy(SearchingKey &key) {
auto& idx = m_pMultiIndex.template get<TagType>();
auto& stats = GetStats<TagType>();

auto it = idx.find(key);
++(it == idx.end()? stats.searchedNotFound : stats.searchedSuccessfully);

return it;
}

void Insert(ValueType const &key) {
std::cout << (m_pMultiIndex.insert(key).second? "success":"failed") << std::endl;
}

private:
std::vector<SrStatisticsByIndex> m_StatsByIndex { NumberOfIndexes() };
};

class CrUsersValue {
int val1;
int val2;
};

class CrUsersKeys {
public:
int IMSI;
int TIMESTAMP;
CrUsersValue val;
};

typedef boost::multi_index::multi_index_container<
CrUsersKeys,
bmi::indexed_by<
bmi::ordered_non_unique<bmi::tag<struct TIMESTAMP_tag>,
bmi::member<CrUsersKeys, int, &CrUsersKeys::TIMESTAMP> >,
bmi::hashed_unique<bmi::tag<struct IMSI_tag>,
bmi::member<CrUsersKeys, int, &CrUsersKeys::IMSI> /*, boost::hash<int>, std::equal_to<int>*/>
>
/*, bip::allocator<CrUsersKeys,bip::managed_shared_memory::segment_manager>*/
>
GlobalHash;

int main() {
CrMultiIndex<GlobalHash> multi;

CrUsersKeys key;
key.IMSI = 2;
multi.Insert(key);

int searchKey = 2;
auto it = multi.GetIteratorBy<IMSI_tag>(searchKey);
if (it != multi.m_pMultiIndex.get<IMSI_tag>().end())
std::cout << "found " << std::endl;
}

打印

success
found

关于boost - 查找 boost multi index 标签到索引和索引数量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49232257/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com