multi_pass.hpp

来自「Boost provides free peer-reviewed portab」· HPP 代码 · 共 1,308 行 · 第 1/3 页

HPP
1,308
字号
        // and access the m_input data member.        template <typename MultiPassT>        static void increment(MultiPassT& mp)        {            if (mp.queuePosition == mp.queuedElements->end())            {                // don't let the queue get larger than N                if (mp.queuedElements->size() >= N)                    mp.queuedElements->pop_front();                mp.queuedElements->push_back(mp.get_input());                mp.advance_input();            }            ++mp.queuePosition;        }        // no-op        void clear_queue()        {}        // called to determine whether the iterator is an eof iterator        template <typename MultiPassT>        static bool is_eof(MultiPassT const& mp)        {            return mp.queuePosition == mp.queuedElements->end() &&                mp.input_at_eof();        }        // called by operator==        bool equal_to(inner const& x) const        {            return queuePosition == x.queuePosition;        }        // called by operator<        bool less_than(inner const& x) const        {            return queuePosition < x.queuePosition;        }}; // class inner}; // class fixed_size_queue///////////////////////////////////////////////////////////////////////////////// class input_iterator// Implementation of the InputPolicy used by multi_pass// input_iterator encapsulates an input iterator of type InputT///////////////////////////////////////////////////////////////////////////////class input_iterator{    public:template <typename InputT>class inner{    private:        typedef            typename boost::detail::iterator_traits<InputT>::value_type            result_type;    public:        typedef result_type value_type;    private:        struct Data {            Data(InputT const &input_)             :   input(input_), was_initialized(false)            {}                        InputT input;            value_type curtok;            bool was_initialized;        };       // Needed by compilers not implementing the resolution to DR45. For       // reference, see       // http://www.open-std.org/JTC1/SC22/WG21/docs/cwg_defects.html#45.       friend struct Data;    public:        typedef            typename boost::detail::iterator_traits<InputT>::difference_type            difference_type;        typedef            typename boost::detail::iterator_traits<InputT>::pointer            pointer;        typedef            typename boost::detail::iterator_traits<InputT>::reference            reference;    protected:        inner()            : data(0)        {}        inner(InputT x)            : data(new Data(x))        {}        inner(inner const& x)            : data(x.data)        {}        void destroy()        {            delete data;            data = 0;        }        bool same_input(inner const& x) const        {            return data == x.data;        }        typedef            typename boost::detail::iterator_traits<InputT>::value_type            value_t;        void swap(inner& x)        {            impl::mp_swap(data, x.data);        }        void ensure_initialized() const        {            if (data && !data->was_initialized) {                data->curtok = *data->input;      // get the first token                data->was_initialized = true;            }        }    public:        reference get_input() const        {            BOOST_SPIRIT_ASSERT(NULL != data);            ensure_initialized();            return data->curtok;        }        void advance_input()        {            BOOST_SPIRIT_ASSERT(NULL != data);            data->was_initialized = false;        // should get the next token            ++data->input;        }        bool input_at_eof() const        {            return !data || data->input == InputT();        }    private:        Data *data;};};///////////////////////////////////////////////////////////////////////////////// class lex_input// Implementation of the InputPolicy used by multi_pass// lex_input gets tokens (ints) from yylex()///////////////////////////////////////////////////////////////////////////////class lex_input{    public:template <typename InputT>class inner{    public:        typedef int value_type;    typedef std::ptrdiff_t difference_type;        typedef int* pointer;        typedef int& reference;    protected:        inner()            : curtok(new int(0))        {}        inner(InputT x)            : curtok(new int(x))        {}        inner(inner const& x)            : curtok(x.curtok)        {}        void destroy()        {            delete curtok;            curtok = 0;        }        bool same_input(inner const& x) const        {            return curtok == x.curtok;        }        void swap(inner& x)        {            impl::mp_swap(curtok, x.curtok);        }    public:        reference get_input() const        {            return *curtok;        }        void advance_input()        {            extern int yylex();            *curtok = yylex();        }        bool input_at_eof() const        {            return *curtok == 0;        }    private:        int* curtok;};};///////////////////////////////////////////////////////////////////////////////// class functor_input// Implementation of the InputPolicy used by multi_pass// functor_input gets tokens from a functor// Note: the functor must have a typedef for result_type// It also must have a static variable of type result_type defined to// represent eof that is called eof.///////////////////////////////////////////////////////////////////////////////class functor_input{    public:template <typename FunctorT>class inner{    typedef typename FunctorT::result_type result_type;    public:        typedef result_type value_type;    typedef std::ptrdiff_t difference_type;        typedef result_type* pointer;        typedef result_type& reference;    protected:        inner()            : ftor(0)            , curtok(0)        {}        inner(FunctorT const& x)            : ftor(new FunctorT(x))            , curtok(new result_type((*ftor)()))        {}        inner(inner const& x)            : ftor(x.ftor)            , curtok(x.curtok)        {}        void destroy()        {            delete ftor;            ftor = 0;            delete curtok;            curtok = 0;        }        bool same_input(inner const& x) const        {            return ftor == x.ftor;        }        void swap(inner& x)        {            impl::mp_swap(curtok, x.curtok);            impl::mp_swap(ftor, x.ftor);        }    public:        reference get_input() const        {            return *curtok;        }        void advance_input()        {            if (curtok) {                *curtok = (*ftor)();            }        }        bool input_at_eof() const        {            return !curtok || *curtok == ftor->eof;        }        FunctorT& get_functor() const        {            return *ftor;        }    private:        FunctorT* ftor;        result_type* curtok;};};} // namespace multi_pass_policies///////////////////////////////////////////////////////////////////////////////// iterator_base_creator///////////////////////////////////////////////////////////////////////////////namespace iterator_ { namespace impl {// Meta-function to generate a std::iterator<> base class for multi_pass. This//  is used mainly to improve conformance of compilers not supporting PTS//  and thus relying on inheritance to recognize an iterator.// We are using boost::iterator<> because it offers an automatic workaround//  for broken std::iterator<> implementations.template <typename InputPolicyT, typename InputT>struct iterator_base_creator{    typedef typename InputPolicyT::BOOST_NESTED_TEMPLATE inner<InputT> input_t;    typedef boost::iterator    <        std::forward_iterator_tag,        typename input_t::value_type,        typename input_t::difference_type,        typename input_t::pointer,        typename input_t::reference    > type;};}}///////////////////////////////////////////////////////////////////////////////// class template multi_pass ///////////////////////////////////////////////////////////////////////////////// The default multi_pass instantiation uses a ref-counted std_deque scheme.template<    typename InputT,    typename InputPolicy,    typename OwnershipPolicy,    typename CheckingPolicy,    typename StoragePolicy>class multi_pass    : public OwnershipPolicy    , public CheckingPolicy    , public StoragePolicy::template inner<                typename InputPolicy::template inner<InputT>::value_type>    , public InputPolicy::template inner<InputT>    , public iterator_::impl::iterator_base_creator<InputPolicy, InputT>::type{        typedef OwnershipPolicy OP;        typedef CheckingPolicy CHP;        typedef typename StoragePolicy::template inner<            typename InputPolicy::template inner<InputT>::value_type> SP;        typedef typename InputPolicy::template inner<InputT> IP;        typedef typename            iterator_::impl::iterator_base_creator<InputPolicy, InputT>::type            IB;    public:        typedef typename IB::value_type value_type;        typedef typename IB::difference_type difference_type;        typedef typename IB::reference reference;        typedef typename IB::pointer pointer;        typedef InputT iterator_type;        multi_pass();        explicit multi_pass(InputT input);#if BOOST_WORKAROUND(__GLIBCPP__, == 20020514)        multi_pass(int);#endif // BOOST_WORKAROUND(__GLIBCPP__, == 20020514)        ~multi_pass();        multi_pass(multi_pass const&);        multi_pass& operator=(multi_pass const&);        void swap(multi_pass& x);        reference operator*() const;        pointer operator->() const;        multi_pass& operator++();        multi_pass operator++(int);        void clear_queue();        bool operator==(const multi_pass& y) const;        bool operator<(const multi_pass& y) const;    private: // helper functions        bool is_eof() const;};template<    typename InputT,    typename InputPolicy,    typename OwnershipPolicy,    typename CheckingPolicy,    typename StoragePolicy>inlinemulti_pass<InputT, InputPolicy, OwnershipPolicy, CheckingPolicy, StoragePolicy>::multi_pass()    : OP()    , CHP()    , SP()    , IP(){}template<    typename InputT,    typename InputPolicy,    typename OwnershipPolicy,

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?