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

Increment the Iterator pointing into a Container Attribute

Boost , Spirit 2.5.2 , Extract Attribute Values to Generate Output from a Container (Karma)

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

PrevUpHomeNext
next_iterator

Шаблон<next_iterator>— это тип, используемый в качестве точки настройки атрибута. На него ссылаетсяКарма.повторяющиеся генераторы (такие какСписок (<%>),Клин (унитарный<*>),Плюс (унар.<+>)иПовторитьдля того, чтобы получить итератор, указывающий на следующий элемент контейнера, держащего атрибуты для генерации вывода из.

Module Headers
#include <boost/spirit/home/support/container.hpp>

См. такжеВключить структуру.

[Note]Note

Этот файл заголовка не должен быть включен непосредственно какой-либо пользовательской программой, поскольку он обычно включается другими файлами заголовка Spirit, основанными на его содержании.

Namespace

Имя

<boost::spirit::traits>

Synopsis
template <typename Iterator, typename Enable>
struct next_iterator
{
    static void call(Iterator& it);
};
Template parameters

Параметр

Описание

по умолчанию

<Iterator>

Тип<Iterator>итератора для увеличения. Это то же самое, что и тип, возвращаемый точкой настройки<traits::container_iterator>

.

Нет

<Enable>

Параметр шаблона помощника, используемый для выборочного включения или отключения определенных специализаций<next_iterator>с использованием SFINAE (то есть<boost::enable_if>или<boost::disable_if>).

<void>

Notation

Iterator

Тип итератора.

it

Пример итератора типа<Iterator>.

C

Тип контейнера, тип итератора которого<Iterator>.

Expression Semantics

выражение

Семантика

<next_iterator<Iterator>::call(it)>

Увеличьте итератор так, чтобы он указывал на следующий элемент.

Predefined Specializations

Духпредопределяет специализацию этой точки настройки для нескольких типов. В следующей таблице перечислены эти типы вместе с типами, возвращаемыми встроенным typedef<type>:

Параметры шаблонов

Семантика

<Iterator>

Исполнители<++it>

.

<unused_type>< const*>

Ничего не делает.

When to implement

Точка настройки<next_iterator>должна быть реализована для конкретного типа итератора, когда контейнер, к которому принадлежит этот итератор, должен использоваться в качестве атрибута вместо контейнера STL. Он применим для генераторовДуха. Только карма. Как правило, он должен быть реализован всякий раз, когда определенный тип итератора принадлежит контейнеру, который должен быть передан в качестве атрибута генератору, обычно подвергающему контейнер STL<C>, и если тип контейнера не подвергает интерфейс контейнера STL (то есть<is_container<C>::type>обычно возвращается<mpl::false_>).

Related Attribute Customization Points

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

Example

Вот файлы заголовка, необходимые для компиляции примерного кода ниже:

#include <boost/spirit/include/karma.hpp>
#include <iostream>
#include <string>
#include <vector>

Пример (полный исходный код см. здесь:customize_use_as_container.cpp) использует структуру данных

namespace client
{
    struct use_as_container
    {
        // Expose a pair holding a pointer to the use_as_container and to the 
        // current element as our iterator.
        // We intentionally leave out having it a 'operator==()' to demonstrate
        // the use of the 'compare_iterators' customization point.
        struct iterator
        {
            iterator(use_as_container const* container, int const* current)
              : container_(container), current_(current)
            {}
            use_as_container const* container_;
            int const* current_;
        };
        // expose 'int' as the type of each generated element
        typedef int type;
        use_as_container(int value1, int value2, int value3)
          : value1_(value1), value2_(value2), value3_(value3)
        {}
        int value1_;
        std::string dummy1_;    // insert some unrelated data
        int value2_;
        std::string dummy2_;    // insert some more unrelated data
        int value3_;
    };
}

В качестве прямого атрибута кСписку<%>генератору. Этот тип не раскрывает ни один из интерфейсов контейнера STL. Он даже не раскрывает привычную семантику контейнера. Целью этого искусственного примера является демонстрация того, как точки настройки могут использоваться для раскрытия независимых элементов данных в виде единого контейнера. Пример показывает, как включить его использование в качестве атрибута.Кармаповторяющиеся генераторы.

Чтобы сделать эту структуру данных совместимой, нам нужно специализироваться на нескольких точках настройки атрибутов:<traits::is_container>,<traits::container_iterator>,<traits::begin_container>и<traits::end_container>. Кроме того, мы специализируемся на всех точках настройки, связанных с итератором:<traits::deref_iterator>,<traits::next_iterator>и<traits::compare_iterators>.

// All specializations of attribute customization points have to be placed into
// the namespace boost::spirit::traits.
//
// Note that all templates below are specialized using the 'const' type.
// This is necessary as all attributes in Karma are 'const'.
namespace boost { namespace spirit { namespace traits
{
    // The specialization of the template 'is_container<>' will tell the 
    // library to treat the type 'client::use_as_container' as a 
    // container holding the items to generate output from.
    template <>
    struct is_container<client::use_as_container const>
      : mpl::true_
    {};
    // The specialization of the template 'container_iterator<>' will be
    // invoked by the library to evaluate the iterator type to be used
    // for iterating the data elements in the container. We simply return
    // the type of the iterator exposed by the embedded 'std::vector<int>'.
    template <>
    struct container_iterator<client::use_as_container const>
    {
        typedef client::use_as_container::iterator type;
    };
    // The specialization of the templates 'begin_container<>' and 
    // 'end_container<>' below will be used by the library to get the iterators 
    // pointing to the begin and the end of the data to generate output from. 
    //
    // The passed argument refers to the attribute instance passed to the list 
    // generator.
    template <>
    struct begin_container<client::use_as_container const>
    {
        static client::use_as_container::iterator
        call(client::use_as_container const& c)
        {
            return client::use_as_container::iterator(&c, &c.value1_);
        }
    };
    template <>
    struct end_container<client::use_as_container const>
    {
        static client::use_as_container::iterator
        call(client::use_as_container const& c)
        {
            return client::use_as_container::iterator(&c, (int const*)0);
        }
    };
}}}

// All specializations of attribute customization points have to be placed into
// the namespace boost::spirit::traits.
namespace boost { namespace spirit { namespace traits
{
    // The specialization of the template 'deref_iterator<>' will be used to 
    // dereference the iterator associated with our counter data structure.
    template <>
    struct deref_iterator<client::use_as_container::iterator>
    {
        typedef client::use_as_container::type type;
        static type call(client::use_as_container::iterator const& it)
        {
            return *it.current_;
        }
    };
    template <>
    struct next_iterator<client::use_as_container::iterator>
    {
        static void call(client::use_as_container::iterator& it)
        {
            if (it.current_ == &it.container_->value1_)
                it.current_ = &it.container_->value2_;
            else if (it.current_ == &it.container_->value2_)
                it.current_ = &it.container_->value3_;
            else
                it.current_ = 0;
        }
    };
    template <>
    struct compare_iterators<client::use_as_container::iterator>
    {
        static bool call(client::use_as_container::iterator const& it1
          , client::use_as_container::iterator const& it2)
        {
            return it1.current_ == it2.current_ &&
                   it1.container_ == it2.container_;
        }
    };
}}}

Последний фрагмент кода показывает пример, использующий экземпляр структуры данных<client::use_as_container>для генерации вывода изСписка<%>генератора:

client::use_as_container d2 (1, 2, 3);
// use the instance of a 'client::use_as_container' instead of a STL vector
std::cout << karma::format(karma::int_ % ", ", d2) << std::endl;   // prints: '1, 2, 3'

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


PrevUpHomeNext

Статья Increment the Iterator pointing into a Container Attribute раздела Spirit 2.5.2 Extract Attribute Values to Generate Output from a Container (Karma) может быть полезна для разработчиков на c++ и boost.




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



:: Главная :: Extract Attribute Values to Generate Output from a Container (Karma) ::


реклама


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

Время компиляции файла: 2024-08-30 11:47:00
2025-05-19 20:32:20/0.028631925582886/1