Карта сайта Kansoftware
НОВОСТИУСЛУГИРЕШЕНИЯКОНТАКТЫ
Разработка программного обеспечения

Boost.MultiIndex Documentation - Tutorial - Container creation

Boost , , Boost.MultiIndex Documentation - Tutorial

Boost C++ Libraries

...one of the most highly regarded and expertly designed C++ library projects in the world. Herb Sutter and Andrei Alexandrescu, C++ Coding Standards

Boost.MultiIndex Tutorial: Container creation



Contents

Value semantics

<multi_index_container>s имеют обычную семантику значений, связанную с копированием конструкции и присвоением, т.е. копии элементов из исходного контейнера создаются и вставляются в контейнер назначения. Более интересно, что копирование также воссоздает исходный порядок, в котором элементы расположены длякаждого индексаконтейнера. Это означает, что равенство всех индексов сохраняется при копировании или присвоении для тех типов индексов, в которых определяется равенство. Это поведение можно рассматривать как естественное продолжение общего правила о семантике копий, утверждающего, что если<y>является копией<x>, то<y==x>.

Use of ctor_args_list

Хотя в большинстве случаев<multi_index_container>s будут построены по умолчанию (или скопированы с ранее существовавшего<multi_index_container>), иногда необходимо указать конкретные значения для используемых внутренних объектов (ключевые экстракторы, сравнительные предикаты, распределитель), например, если некоторые из этих объектов не имеют конструктора по умолчанию. Такая же ситуация может возникнуть и со стандартными STL-контейнерами, которые допускают опциональную спецификацию таких объектов:

// example of non-default constructed std::set
template<typename IntegralType>
struct modulo_less
{
  modulo_less(IntegralType m):modulo(m){}
  bool operator()(IntegralType x,IntegralType y)const
  {
    return (x%modulo)<(y%modulo);
  }
private:
  IntegralType modulo;
};
typedef std::set<unsigned int,modulo_less<unsigned int> > modulo_set;
modulo_set m(modulo_less<unsigned int>(10));

<multi_index_container>также обеспечивает эту функциональность, хотя и значительно более сложным образом, в связи с тем, что конструктор<multi_index_container>должен принимать значения для всех внутренних объектов своих индексов. Полная форма<multi_index_container>конструктора

explicit multi_index_container(
    const ctor_args_list& args_list=ctor_args_list(),
    const allocator_type& al=allocator_type());

Спецификация объекта-распределителя не представляет особых проблем; что касается<ctor_args_list>, то этот объект спроектирован таким образом, чтобы удерживать необходимые значения конструкции для каждого индекса в<multi_index_container>. С точки зрения пользователя<ctor_args_list>эквивалентен типу

boost::tuple<C0,...,CI-1>

где<I>— число индексов, а<Ci>— число индексов.

nth_index<i>::type::ctor_args

То есть вложенного типа<ctor_args>из<i>-го индекса. Каждый<ctor_args>тип, в свою очередь, представляет собой набор удерживающих значений для аргументов конструктора связанного индекса: так, упорядоченные индексы требуют ключевого объекта-экстрактора и сравнительного предиката, хешированные индексы берут начальное число ведер, ключевой экстрактор, хеш-функцию и предикат равенства; в то время как индексы секвенированного и случайного доступа не нуждаются в каком-либо аргументе построения. Например, учитывая определение

typedef multi_index_container<
  unsigned int,
  indexed_by<
    hashed_unique<identity<unsigned int> >,
    ordered_non_unique<identity<unsigned int>, modulo_less<unsigned int> >,
    sequenced<>,
    random_access<>
  >
> modulo_indexed_set;

Соответствующий<ctor_args_list>тип эквивалентен

boost::tuple<
  // ctr_args of index #0
  boost::tuple<
    std::size_t, // initial number of buckets; 0 if unspecified
    identity<unsigned int>,
    boost::hash<unsigned int>,
    std::equal_to<unsigned int> >,    
  // ctr_args of index #1
  boost::tuple<
    identity<unsigned int>,
    modulo_less<unsigned int> >,
  
  // sequenced indices do not have any construction argument
  boost::tuple<>,
  // neither do random access indices
  boost::tuple<>
>

Такой<modulo_indexed_set>не может быть построен по умолчанию, потому что<modulo_less>не обеспечивает конструктор по умолчанию. Ниже показано, как можно построить:

modulo_indexed_set::ctor_args_list args_list=
  boost::make_tuple(
    // ctor_args for index #0 is default constructible
    modulo_indexed_set::nth_index<0>::type::ctor_args(),
    
    boost::make_tuple(identity<unsigned int>(),modulo_less<unsigned int>(10)),
    
    // these are also default constructible (actually, empty tuples) 
    modulo_indexed_set::nth_index<2>::type::ctor_args(),
    modulo_indexed_set::nth_index<3>::type::ctor_args()
  );
modulo_indexed_set m(args_list);

В разделепримеровприведена программа, которая применяет на практике эти концепции.

Special allocator support

Повышаю. MultiIndex допускает немного более общий класс распределителей, чем строго требуется стандартом C++, как подробно объясняется в ссылке. Важным типом поддерживаемых нестандартных распределителей являются те, которые предоставляются библиотекойBoost Interprocess Library; это открывает возможность размещения<multi_index_container>s в общей памяти.

#include <boost/interprocess/allocators/allocator.hpp>
#include <boost/interprocess/managed_shared_memory.hpp>
namespace bip=boost::interprocess;
// a shared memory compatible allocator of ints
typedef bip::allocator<
  int,bip::managed_shared_memory::segment_manager
> shared_int_allocator;
// define a shared memory compatible multi_index_container
// using shared_int_allocator
typedef multi_index_container<
  int,
  indexed_by<
    sequenced<>,
    ordered_unique<identity<int> >
  >,
  shared_int_allocator
> unique_int_list;
...
// create a managed memory segment
bip::managed_shared_memory seg(
  bip::create_only,"SharedMemoryID",65536);
// construct a unique_int_list into the segment
unique_int_list* puil=seg.construct<unique_int_list>
  ("UniqueIntListID") // object identifier within the segment
  // Construction args: first a ctor arg list, then a
  // shared memory allocator obtained from the segment object.
  (unique_int_list::ctor_args_list(),
   unique_int_list::allocator_type(seg.get_segment_manager()));
   

Примеры включают в себяпрограмму, которая дополнительно исследует эту возможность.

Serialization

<multi_index_container>может быть заархивировано и извлечено с помощьюБиблиотеки сериализации. Поддерживаются как обычные, так и XML-архивы. Использование является простым и не отличается от любого другого серийного типа. Например:

#include <boost/archive/text_oarchive.hpp>
#include <boost/archive/text_iarchive.hpp>
#include <fstream>
...
void save(const employee_set& es)
{
  std::ofstream ofs("data");
  boost::archive::text_oarchive oa(ofs);
  oa<<es;
}
void load(employee_set& es)
{
  std::ifstream ifs("data");
  boost::archive::text_iarchive ia(ifs);
  ia>>es;
}
...
employee_set es;
... // fill it with data
save(es);
...
employee_set restored_es;
load(restored_es);

Возможности сериализации автоматически предоставляются путем простого соединения с соответствующим усилителем. Модуль библиотеки сериализации: нет необходимости явно включать любой заголовок из Boost. Сериализация, кроме объявлений типа архива, используемого в процессе. Если не используется, поддержка сериализации может быть отключена путем глобального определения макроса<BOOST_MULTI_INDEX_DISABLE_SERIALIZATION>. Отключение сериализации для повышения. MultiIndex может дать небольшое улучшение во времени сборки и может быть необходим в тех неисправных компиляторах, которые не могут правильно обрабатывать заголовки Boost.Serialization.

В соответствии с Boost.MultiIndexзначение семантики, извлечение архивного<multi_index_container>восстанавливает не только элементы, но и порядок, в котором они были расположены для каждого индекса контейнера. Однако есть исключение из этого правила: дляхешированных индексовне гарантируется порядок итерации элементов в восстановленном контейнере; в целом неразумно полагаться на упорядочение элементов хешированного индекса, поскольку он может произвольно изменяться при вставке или перетасовке — именно поэтому хешированные индексы и неупорядоченные ассоциативные контейнеры TR1 не определяют оператора равенства.

Итераторы к индексам<multi_index_container>также могут быть сериализованы. Сериализация итераторов должна производиться только после сериализации их соответствующего контейнера.

Пример 9в разделе примеров показывает возможности сериализации Boost. MultiIndex.




Пересмотрено 17 июля 2007 года

© Copyright 2003-2007 Joaquín M López Muñoz. Распространяется под лицензией Boost Software License, версия 1.0. (См. сопроводительный файлLICENSE_1_0.txtили копию по адресуhttp://www.boost.org/LICENSE_1_0.txt)

Статья Boost.MultiIndex Documentation - Tutorial - Container creation раздела Boost.MultiIndex Documentation - Tutorial может быть полезна для разработчиков на c++ и boost.




Материалы статей собраны из открытых источников, владелец сайта не претендует на авторство. Там где авторство установить не удалось, материал подаётся без имени автора. В случае если Вы считаете, что Ваши права нарушены, пожалуйста, свяжитесь с владельцем сайта.



:: Главная :: Boost.MultiIndex Documentation - Tutorial ::


реклама


©KANSoftWare (разработка программного обеспечения, создание программ, создание интерактивных сайтов), 2007
Top.Mail.Ru

Время компиляции файла: 2024-08-30 11:47:00
2025-05-20 04:07:33/0.0052440166473389/0