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

Extensibility

Boost , The Boost C++ Libraries BoostBook Documentation Subset , Chapter 12. Boost.Foreach

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

Если мы хотим использовать<BOOST_FOREACH>для итерации по новому типу коллекции, мы должны «научить»<BOOST_FOREACH>взаимодействовать с нашим типом. С тех пор<BOOST_FOREACH>Построен на вершинеBoost.Range, мы должны увеличить.Чтобы увеличить<BOOST_FOREACH>. СекцияРасширение. диапазонподробно рассматривает эту тему.

Ниже приведен пример для расширения<BOOST_FOREACH>для итерации по подструнному типу, который содержит два итератора в<std::string>.

namespace my
{
    // sub_string: part of a string, as delimited by a pair
    // of iterators
    struct sub_string
    {
        std::string::iterator begin;
        std::string::iterator end;
        /* ... implementation ... */
    };
    // Add overloads of range_begin() and range_end() in the
    // same namespace as sub_string, to be found by Argument-Dependent Lookup.
    inline std::string::iterator range_begin( sub_string & x )
    {
        return x.begin;
    }
    inline std::string::iterator range_end( sub_string & x )
    {
        return x.end;
    }
    // Also add overloads for const sub_strings. Note we use the conversion
    // from string::iterator to string::const_iterator here.
    inline std::string::const_iterator range_begin( sub_string const & x )
    {
        return x.begin;
    }
    inline std::string::const_iterator range_end( sub_string const & x )
    {
        return x.end;
    }
}
namespace boost
{
    // specialize range_mutable_iterator and range_const_iterator in namespace boost
    template<>
    struct range_mutable_iterator< my::sub_string >
    {
        typedef std::string::iterator type;
    };
    template<>
    struct range_const_iterator< my::sub_string >
    {
        typedef std::string::const_iterator type;
    };
}

Теперь, когда мы научилиBoost.Range(и, следовательно,<BOOST_FOREACH>) о нашем типе, мы можем теперь использовать<BOOST_FOREACH>для итерации над нашим подстрочным типом.

my::sub_string substr;
BOOST_FOREACH( char ch, substr )
{
    // Woo-hoo!
}

Есть некоторые проблемы переносимости, о которых мы должны знать при расширении<BOOST_FOREACH>. Обязательно проверьте разделПортативность. В частности, если ваш компилятор не поддерживает Argument-Dependent Lookup,Boost. Диапазон портативностираздел предлагает некоторые предлагаемые обходные пути.

Making BOOST_FOREACH Work with Non-Copyable Sequence Types

Для типов последовательностей, которые не являются копируемыми, нам нужно будет сказать<BOOST_FOREACH>, чтобы не пытаться делать копии. Если наш тип наследует от<boost::noncopyable>, никаких дальнейших действий не требуется. Если нет, мы должны специализировать шаблон<boost::foreach::is_noncopyable<>>следующим образом:

class noncopy_vector
{
    // ...
private:
    noncopy_vector( noncopy_vector const & ); // non-copyable!
};
namespace boost { namespace foreach
{
    template<>
    struct is_noncopyable< noncopy_vector >
      : mpl::true_
    {
    };
}}

Другой способ добиться такого же эффекта — переопределить глобальную функцию<boost_foreach_is_noncopyable()>. Делая это таким образом, имеет преимущество быть портативным для старых компиляторов.

// At global scope...
inline boost::mpl::true_ *
boost_foreach_is_noncopyable( noncopy_vector *&, boost::foreach::tag )
{
    return 0;
}
[Tip] Tip

Хотя мы должны сказать<BOOST_FOREACH>, что наш тип не является копируемым, это не означает, что<BOOST_FOREACH>всегда делает копию нашего типа последовательности. Очевидно, что это будет дорого и даже неправильно в некоторых случаях.<BOOST_FOREACH>довольно умно о том, когда делать копию, а когда нет.<is_noncopyable<>>черта необходима, чтобы удалить копию, которая находится на ветке, которая может никогда не быть взята.

Optimizing BOOST_FOREACH for Lightweight Proxy Sequence Types

На некоторых компиляторах<BOOST_FOREACH>иногда требуется несколько более медленный путь кода, чтобы гарантировать правильную обработку последовательностей, хранящихся во временных объектах. Он спрашивает себя: «Должен ли я сделать копию этого объекта?», а затем: «Я сделал копию или нет?» Для некоторых типов последовательностей это перебор. Рассмотрим последовательность, которая представляет собой простую пару итераторов. Прыгать через обручи огня, чтобы избежать копирования, не имеет смысла, потому что копирование очень дешево.

Пара итераторов является примером легкого прокси. Он не хранит значения последовательности; скорее, он хранит итераторы для них. Это означает, что повторение над копией прокси-объекта даст те же результаты, что и использование самого объекта. Для таких типов<BOOST_FOREACH>обеспечивает крючок, который позволяет нам сказать ему, чтобы он не беспокоился о расходах на изготовление копии. Это может привести к немного более быстрому выполнению цикла. Просто специализируйте черту<boost::foreach::is_lightweight_proxy<>>следующим образом:

struct sub_string
  : boost::iterator_range< std::string::iterator >
{
    // ...
};
namespace boost { namespace foreach
{
    template<>
    struct is_lightweight_proxy< sub_string >
      : mpl::true_
    {
    };
}}

С другой стороны, мы могли бы достичь того же эффекта, переопределив глобальную функцию<boost_foreach_is_lightweight_proxy()>следующим образом:

// At global scope...
inline boost::mpl::true_ *
boost_foreach_is_lightweight_proxy( sub_string *&, boost::foreach::tag )
{
    return 0;
}

Этот метод переносим на более старые компиляторы.


PrevUpHomeNext

Статья Extensibility раздела The Boost C++ Libraries BoostBook Documentation Subset Chapter 12. Boost.Foreach может быть полезна для разработчиков на c++ и boost.




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



:: Главная :: Chapter 12. Boost.Foreach ::


реклама


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

Время компиляции файла: 2024-08-30 11:47:00
2025-05-19 17:27:15/0.0072610378265381/0