Imported existing code
This commit is contained in:
@@ -0,0 +1,366 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Joel de Guzman
|
||||
Copyright (c) 2001-2003 Daniel Nuffer
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_CHSET_IPP
|
||||
#define BOOST_SPIRIT_CHSET_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <boost/limits.hpp>
|
||||
#include <boost/spirit/home/classic/utility/chset.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// chset class
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace utility { namespace impl {
|
||||
template <typename CharT>
|
||||
inline void
|
||||
detach(boost::shared_ptr<basic_chset<CharT> >& ptr)
|
||||
{
|
||||
if (!ptr.unique())
|
||||
ptr = boost::shared_ptr<basic_chset<CharT> >
|
||||
(new basic_chset<CharT>(*ptr));
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
detach_clear(boost::shared_ptr<basic_chset<CharT> >& ptr)
|
||||
{
|
||||
if (ptr.unique())
|
||||
ptr->clear();
|
||||
else
|
||||
ptr.reset(new basic_chset<CharT>());
|
||||
}
|
||||
|
||||
template <typename CharT, typename CharT2>
|
||||
void construct_chset(boost::shared_ptr<basic_chset<CharT> >& ptr,
|
||||
CharT2 const* definition)
|
||||
{
|
||||
CharT2 ch = *definition++;
|
||||
while (ch)
|
||||
{
|
||||
CharT2 next = *definition++;
|
||||
if (next == '-')
|
||||
{
|
||||
next = *definition++;
|
||||
if (next == 0)
|
||||
{
|
||||
ptr->set(ch);
|
||||
ptr->set('-');
|
||||
break;
|
||||
}
|
||||
ptr->set(ch, next);
|
||||
}
|
||||
else
|
||||
{
|
||||
ptr->set(ch);
|
||||
}
|
||||
ch = next;
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT, typename FakeT>
|
||||
void chset_negated_set(boost::shared_ptr<basic_chset<CharT> > &ptr, chlit<CharT> const &ch,
|
||||
FakeT)
|
||||
{
|
||||
if(ch.ch != (std::numeric_limits<CharT>::min)()) {
|
||||
ptr->set((std::numeric_limits<CharT>::min)(), ch.ch - 1);
|
||||
}
|
||||
if(ch.ch != (std::numeric_limits<CharT>::max)()) {
|
||||
ptr->set(ch.ch + 1, (std::numeric_limits<CharT>::max)());
|
||||
}
|
||||
}
|
||||
|
||||
template <typename CharT, typename FakeT>
|
||||
void chset_negated_set(boost::shared_ptr<basic_chset<CharT> > &ptr,
|
||||
spirit::range<CharT> const &rng, FakeT)
|
||||
{
|
||||
if(rng.first != (std::numeric_limits<CharT>::min)()) {
|
||||
ptr->set((std::numeric_limits<CharT>::min)(), rng.first - 1);
|
||||
}
|
||||
if(rng.last != (std::numeric_limits<CharT>::max)()) {
|
||||
ptr->set(rng.last + 1, (std::numeric_limits<CharT>::max)());
|
||||
}
|
||||
}
|
||||
|
||||
#endif // BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
//////////////////////////////////
|
||||
|
||||
}} // namespace utility::impl
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset()
|
||||
: ptr(new basic_chset<CharT>()) {}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(chset const& arg_)
|
||||
: ptr(new basic_chset<CharT>(*arg_.ptr)) {}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(CharT arg_)
|
||||
: ptr(new basic_chset<CharT>())
|
||||
{ ptr->set(arg_); }
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(anychar_parser /*arg*/)
|
||||
: ptr(new basic_chset<CharT>())
|
||||
{
|
||||
ptr->set(
|
||||
(std::numeric_limits<CharT>::min)(),
|
||||
(std::numeric_limits<CharT>::max)()
|
||||
);
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(nothing_parser arg_)
|
||||
: ptr(new basic_chset<CharT>()) {}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(chlit<CharT> const& arg_)
|
||||
: ptr(new basic_chset<CharT>())
|
||||
{ ptr->set(arg_.ch); }
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(range<CharT> const& arg_)
|
||||
: ptr(new basic_chset<CharT>())
|
||||
{ ptr->set(arg_.first, arg_.last); }
|
||||
|
||||
#if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(negated_char_parser<chlit<CharT> > const& arg_)
|
||||
: ptr(new basic_chset<CharT>())
|
||||
{
|
||||
set(arg_);
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::chset(negated_char_parser<range<CharT> > const& arg_)
|
||||
: ptr(new basic_chset<CharT>())
|
||||
{
|
||||
set(arg_);
|
||||
}
|
||||
|
||||
#endif // !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>::~chset() {}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(chset const& rhs)
|
||||
{
|
||||
ptr = rhs.ptr;
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(CharT rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
ptr->set(rhs);
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(anychar_parser rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
ptr->set(
|
||||
(std::numeric_limits<CharT>::min)(),
|
||||
(std::numeric_limits<CharT>::max)()
|
||||
);
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(nothing_parser rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(chlit<CharT> const& rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
ptr->set(rhs.ch);
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(range<CharT> const& rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
ptr->set(rhs.first, rhs.last);
|
||||
return *this;
|
||||
}
|
||||
|
||||
#if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(negated_char_parser<chlit<CharT> > const& rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
set(rhs);
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator=(negated_char_parser<range<CharT> > const& rhs)
|
||||
{
|
||||
utility::impl::detach_clear(ptr);
|
||||
set(rhs);
|
||||
return *this;
|
||||
}
|
||||
|
||||
#endif // !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
chset<CharT>::set(range<CharT> const& arg_)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
ptr->set(arg_.first, arg_.last);
|
||||
}
|
||||
|
||||
#if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
chset<CharT>::set(negated_char_parser<chlit<CharT> > const& arg_)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
|
||||
if(arg_.positive.ch != (std::numeric_limits<CharT>::min)()) {
|
||||
ptr->set((std::numeric_limits<CharT>::min)(), arg_.positive.ch - 1);
|
||||
}
|
||||
if(arg_.positive.ch != (std::numeric_limits<CharT>::max)()) {
|
||||
ptr->set(arg_.positive.ch + 1, (std::numeric_limits<CharT>::max)());
|
||||
}
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
chset<CharT>::set(negated_char_parser<range<CharT> > const& arg_)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
|
||||
if(arg_.positive.first != (std::numeric_limits<CharT>::min)()) {
|
||||
ptr->set((std::numeric_limits<CharT>::min)(), arg_.positive.first - 1);
|
||||
}
|
||||
if(arg_.positive.last != (std::numeric_limits<CharT>::max)()) {
|
||||
ptr->set(arg_.positive.last + 1, (std::numeric_limits<CharT>::max)());
|
||||
}
|
||||
}
|
||||
|
||||
#endif // !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
chset<CharT>::clear(range<CharT> const& arg_)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
ptr->clear(arg_.first, arg_.last);
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
chset<CharT>::clear(negated_char_parser<range<CharT> > const& arg_)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
|
||||
if(arg_.positive.first != (std::numeric_limits<CharT>::min)()) {
|
||||
ptr->clear((std::numeric_limits<CharT>::min)(), arg_.positive.first - 1);
|
||||
}
|
||||
if(arg_.positive.last != (std::numeric_limits<CharT>::max)()) {
|
||||
ptr->clear(arg_.positive.last + 1, (std::numeric_limits<CharT>::max)());
|
||||
}
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
chset<CharT>::test(CharT ch) const
|
||||
{ return ptr->test(ch); }
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::inverse()
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
ptr->inverse();
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline void
|
||||
chset<CharT>::swap(chset& x)
|
||||
{ ptr.swap(x.ptr); }
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator|=(chset const& x)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
*ptr |= *x.ptr;
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator&=(chset const& x)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
*ptr &= *x.ptr;
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator-=(chset const& x)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
*ptr -= *x.ptr;
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline chset<CharT>&
|
||||
chset<CharT>::operator^=(chset const& x)
|
||||
{
|
||||
utility::impl::detach(ptr);
|
||||
*ptr ^= *x.ptr;
|
||||
return *this;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,107 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Joel de Guzman
|
||||
Copyright (c) 2001-2003 Daniel Nuffer
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_BASIC_CHSET_HPP
|
||||
#define BOOST_SPIRIT_BASIC_CHSET_HPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <bitset>
|
||||
#include <climits>
|
||||
#include <boost/spirit/home/classic/utility/impl/chset/range_run.hpp>
|
||||
#include <boost/spirit/home/classic/namespace.hpp>
|
||||
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// basic_chset: basic character set implementation using range_run
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
class basic_chset
|
||||
{
|
||||
public:
|
||||
basic_chset();
|
||||
basic_chset(basic_chset const& arg_);
|
||||
|
||||
bool test(CharT v) const;
|
||||
void set(CharT from, CharT to);
|
||||
void set(CharT c);
|
||||
void clear(CharT from, CharT to);
|
||||
void clear(CharT c);
|
||||
void clear();
|
||||
|
||||
void inverse();
|
||||
void swap(basic_chset& x);
|
||||
|
||||
basic_chset& operator|=(basic_chset const& x);
|
||||
basic_chset& operator&=(basic_chset const& x);
|
||||
basic_chset& operator-=(basic_chset const& x);
|
||||
basic_chset& operator^=(basic_chset const& x);
|
||||
|
||||
private: utility::impl::range_run<CharT> rr;
|
||||
};
|
||||
|
||||
#if (CHAR_BIT == 8)
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// basic_chset: specializations for 8 bit chars using std::bitset
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
class basic_chset_8bit {
|
||||
|
||||
public:
|
||||
basic_chset_8bit();
|
||||
basic_chset_8bit(basic_chset_8bit const& arg_);
|
||||
|
||||
bool test(CharT v) const;
|
||||
void set(CharT from, CharT to);
|
||||
void set(CharT c);
|
||||
void clear(CharT from, CharT to);
|
||||
void clear(CharT c);
|
||||
void clear();
|
||||
|
||||
void inverse();
|
||||
void swap(basic_chset_8bit& x);
|
||||
|
||||
basic_chset_8bit& operator|=(basic_chset_8bit const& x);
|
||||
basic_chset_8bit& operator&=(basic_chset_8bit const& x);
|
||||
basic_chset_8bit& operator-=(basic_chset_8bit const& x);
|
||||
basic_chset_8bit& operator^=(basic_chset_8bit const& x);
|
||||
|
||||
private: std::bitset<256> bset;
|
||||
};
|
||||
|
||||
/////////////////////////////////
|
||||
template <>
|
||||
class basic_chset<char>
|
||||
: public basic_chset_8bit<char> {};
|
||||
|
||||
/////////////////////////////////
|
||||
template <>
|
||||
class basic_chset<signed char>
|
||||
: public basic_chset_8bit<signed char> {};
|
||||
|
||||
/////////////////////////////////
|
||||
template <>
|
||||
class basic_chset<unsigned char>
|
||||
: public basic_chset_8bit<unsigned char> {};
|
||||
|
||||
#endif
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace BOOST_SPIRIT_CLASSIC_NS
|
||||
|
||||
#endif
|
||||
|
||||
#include <boost/spirit/home/classic/utility/impl/chset/basic_chset.ipp>
|
||||
@@ -0,0 +1,246 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Joel de Guzman
|
||||
Copyright (c) 2001-2003 Daniel Nuffer
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_BASIC_CHSET_IPP
|
||||
#define BOOST_SPIRIT_BASIC_CHSET_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <bitset>
|
||||
#include <boost/spirit/home/classic/utility/impl/chset/basic_chset.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// basic_chset: character set implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset<CharT>::basic_chset() {}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset<CharT>::basic_chset(basic_chset const& arg_)
|
||||
: rr(arg_.rr) {}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
basic_chset<CharT>::test(CharT v) const
|
||||
{ return rr.test(v); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset<CharT>::set(CharT from, CharT to)
|
||||
{ rr.set(utility::impl::range<CharT>(from, to)); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset<CharT>::set(CharT c)
|
||||
{ rr.set(utility::impl::range<CharT>(c, c)); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset<CharT>::clear(CharT from, CharT to)
|
||||
{ rr.clear(utility::impl::range<CharT>(from, to)); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset<CharT>::clear()
|
||||
{ rr.clear(); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset<CharT>::inverse()
|
||||
{
|
||||
basic_chset inv;
|
||||
inv.set(
|
||||
(std::numeric_limits<CharT>::min)(),
|
||||
(std::numeric_limits<CharT>::max)()
|
||||
);
|
||||
inv -= *this;
|
||||
swap(inv);
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset<CharT>::swap(basic_chset& x)
|
||||
{ rr.swap(x.rr); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset<CharT>&
|
||||
basic_chset<CharT>::operator|=(basic_chset<CharT> const& x)
|
||||
{
|
||||
typedef typename utility::impl::range_run<CharT>::const_iterator const_iterator;
|
||||
for (const_iterator iter = x.rr.begin(); iter != x.rr.end(); ++iter)
|
||||
rr.set(*iter);
|
||||
return *this;
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset<CharT>&
|
||||
basic_chset<CharT>::operator&=(basic_chset<CharT> const& x)
|
||||
{
|
||||
basic_chset inv;
|
||||
inv.set(
|
||||
(std::numeric_limits<CharT>::min)(),
|
||||
(std::numeric_limits<CharT>::max)()
|
||||
);
|
||||
inv -= x;
|
||||
*this -= inv;
|
||||
return *this;
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset<CharT>&
|
||||
basic_chset<CharT>::operator-=(basic_chset<CharT> const& x)
|
||||
{
|
||||
typedef typename utility::impl::range_run<CharT>::const_iterator const_iterator;
|
||||
for (const_iterator iter = x.rr.begin(); iter != x.rr.end(); ++iter)
|
||||
rr.clear(*iter);
|
||||
return *this;
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset<CharT>&
|
||||
basic_chset<CharT>::operator^=(basic_chset<CharT> const& x)
|
||||
{
|
||||
basic_chset bma = x;
|
||||
bma -= *this;
|
||||
*this -= x;
|
||||
*this |= bma;
|
||||
return *this;
|
||||
}
|
||||
|
||||
#if (CHAR_BIT == 8)
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// basic_chset: specializations for 8 bit chars using std::bitset
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset_8bit<CharT>::basic_chset_8bit() {}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset_8bit<CharT>::basic_chset_8bit(basic_chset_8bit const& arg_)
|
||||
: bset(arg_.bset) {}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
basic_chset_8bit<CharT>::test(CharT v) const
|
||||
{ return bset.test((unsigned char)v); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::set(CharT from, CharT to)
|
||||
{
|
||||
for (int i = from; i <= to; ++i)
|
||||
bset.set((unsigned char)i);
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::set(CharT c)
|
||||
{ bset.set((unsigned char)c); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::clear(CharT from, CharT to)
|
||||
{
|
||||
for (int i = from; i <= to; ++i)
|
||||
bset.reset((unsigned char)i);
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::clear(CharT c)
|
||||
{ bset.reset((unsigned char)c); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::clear()
|
||||
{ bset.reset(); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::inverse()
|
||||
{ bset.flip(); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
basic_chset_8bit<CharT>::swap(basic_chset_8bit& x)
|
||||
{ std::swap(bset, x.bset); }
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset_8bit<CharT>&
|
||||
basic_chset_8bit<CharT>::operator|=(basic_chset_8bit const& x)
|
||||
{
|
||||
bset |= x.bset;
|
||||
return *this;
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset_8bit<CharT>&
|
||||
basic_chset_8bit<CharT>::operator&=(basic_chset_8bit const& x)
|
||||
{
|
||||
bset &= x.bset;
|
||||
return *this;
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset_8bit<CharT>&
|
||||
basic_chset_8bit<CharT>::operator-=(basic_chset_8bit const& x)
|
||||
{
|
||||
bset &= ~x.bset;
|
||||
return *this;
|
||||
}
|
||||
|
||||
/////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline basic_chset_8bit<CharT>&
|
||||
basic_chset_8bit<CharT>::operator^=(basic_chset_8bit const& x)
|
||||
{
|
||||
bset ^= x.bset;
|
||||
return *this;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,127 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Joel de Guzman
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_RANGE_RUN_HPP
|
||||
#define BOOST_SPIRIT_RANGE_RUN_HPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <vector>
|
||||
|
||||
#include <boost/spirit/home/classic/namespace.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
namespace utility { namespace impl {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// range class
|
||||
//
|
||||
// Implements a closed range of values. This class is used in
|
||||
// the implementation of the range_run class.
|
||||
//
|
||||
// { Low level implementation detail }
|
||||
// { Not to be confused with BOOST_SPIRIT_CLASSIC_NS::range }
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
struct range {
|
||||
|
||||
range(CharT first, CharT last);
|
||||
|
||||
bool is_valid() const;
|
||||
bool includes(CharT v) const;
|
||||
bool includes(range const& r) const;
|
||||
bool overlaps(range const& r) const;
|
||||
void merge(range const& r);
|
||||
|
||||
CharT first;
|
||||
CharT last;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
struct range_char_compare {
|
||||
|
||||
bool operator()(range<CharT> const& x, const CharT y) const
|
||||
{ return x.first < y; }
|
||||
|
||||
bool operator()(const CharT x, range<CharT> const& y) const
|
||||
{ return x < y.first; }
|
||||
|
||||
// This additional operator is required for the checked STL shipped
|
||||
// with VC8 testing the ordering of the iterators passed to the
|
||||
// std::lower_bound algo this range_char_compare<> predicate is passed
|
||||
// to.
|
||||
bool operator()(range<CharT> const& x, range<CharT> const& y) const
|
||||
{ return x.first < y.first; }
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
struct range_compare {
|
||||
|
||||
bool operator()(range<CharT> const& x, range<CharT> const& y) const
|
||||
{ return x.first < y.first; }
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// range_run
|
||||
//
|
||||
// An implementation of a sparse bit (boolean) set. The set uses
|
||||
// a sorted vector of disjoint ranges. This class implements the
|
||||
// bare minimum essentials from which the full range of set
|
||||
// operators can be implemented. The set is constructed from
|
||||
// ranges. Internally, adjacent or overlapping ranges are
|
||||
// coalesced.
|
||||
//
|
||||
// range_runs are very space-economical in situations where there
|
||||
// are lots of ranges and a few individual disjoint values.
|
||||
// Searching is O(log n) where n is the number of ranges.
|
||||
//
|
||||
// { Low level implementation detail }
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
class range_run {
|
||||
|
||||
public:
|
||||
|
||||
typedef range<CharT> range_t;
|
||||
typedef std::vector<range_t> run_t;
|
||||
typedef typename run_t::iterator iterator;
|
||||
typedef typename run_t::const_iterator const_iterator;
|
||||
|
||||
void swap(range_run& rr);
|
||||
bool test(CharT v) const;
|
||||
void set(range_t const& r);
|
||||
void clear(range_t const& r);
|
||||
void clear();
|
||||
|
||||
const_iterator begin() const;
|
||||
const_iterator end() const;
|
||||
|
||||
private:
|
||||
|
||||
void merge(iterator iter, range_t const& r);
|
||||
|
||||
run_t run;
|
||||
};
|
||||
|
||||
}}
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace BOOST_SPIRIT_CLASSIC_NS::utility::impl
|
||||
|
||||
#endif
|
||||
|
||||
#include <boost/spirit/home/classic/utility/impl/chset/range_run.ipp>
|
||||
@@ -0,0 +1,218 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Joel de Guzman
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_RANGE_RUN_IPP
|
||||
#define BOOST_SPIRIT_RANGE_RUN_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <algorithm> // for std::lower_bound
|
||||
#include <boost/spirit/home/classic/core/assert.hpp> // for BOOST_SPIRIT_ASSERT
|
||||
#include <boost/spirit/home/classic/utility/impl/chset/range_run.hpp>
|
||||
#include <boost/spirit/home/classic/debug.hpp>
|
||||
#include <boost/limits.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
namespace utility { namespace impl {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// range class implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline range<CharT>::range(CharT first_, CharT last_)
|
||||
: first(first_), last(last_) {}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
range<CharT>::is_valid() const
|
||||
{ return first <= last; }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
range<CharT>::includes(range const& r) const
|
||||
{ return (first <= r.first) && (last >= r.last); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
range<CharT>::includes(CharT v) const
|
||||
{ return (first <= v) && (last >= v); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
range<CharT>::overlaps(range const& r) const
|
||||
{
|
||||
CharT decr_first =
|
||||
first == (std::numeric_limits<CharT>::min)() ? first : first-1;
|
||||
CharT incr_last =
|
||||
last == (std::numeric_limits<CharT>::max)() ? last : last+1;
|
||||
|
||||
return (decr_first <= r.last) && (incr_last >= r.first);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
range<CharT>::merge(range const& r)
|
||||
{
|
||||
first = (std::min)(first, r.first);
|
||||
last = (std::max)(last, r.last);
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// range_run class implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline bool
|
||||
range_run<CharT>::test(CharT v) const
|
||||
{
|
||||
if (!run.empty())
|
||||
{
|
||||
const_iterator iter =
|
||||
std::lower_bound(
|
||||
run.begin(), run.end(), v,
|
||||
range_char_compare<CharT>()
|
||||
);
|
||||
|
||||
if (iter != run.end() && iter->includes(v))
|
||||
return true;
|
||||
if (iter != run.begin())
|
||||
return (--iter)->includes(v);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
range_run<CharT>::swap(range_run& rr)
|
||||
{ run.swap(rr.run); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
void
|
||||
range_run<CharT>::merge(iterator iter, range<CharT> const& r)
|
||||
{
|
||||
iter->merge(r);
|
||||
iterator i = iter + 1;
|
||||
|
||||
while (i != run.end() && iter->overlaps(*i))
|
||||
iter->merge(*i++);
|
||||
|
||||
run.erase(iter+1, i);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
void
|
||||
range_run<CharT>::set(range<CharT> const& r)
|
||||
{
|
||||
BOOST_SPIRIT_ASSERT(r.is_valid());
|
||||
if (!run.empty())
|
||||
{
|
||||
iterator iter =
|
||||
std::lower_bound(
|
||||
run.begin(), run.end(), r,
|
||||
range_compare<CharT>()
|
||||
);
|
||||
|
||||
if ((iter != run.end() && iter->includes(r)) ||
|
||||
((iter != run.begin()) && (iter - 1)->includes(r)))
|
||||
return;
|
||||
|
||||
if (iter != run.begin() && (iter - 1)->overlaps(r))
|
||||
merge(--iter, r);
|
||||
|
||||
else if (iter != run.end() && iter->overlaps(r))
|
||||
merge(iter, r);
|
||||
|
||||
else
|
||||
run.insert(iter, r);
|
||||
}
|
||||
else
|
||||
{
|
||||
run.push_back(r);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
void
|
||||
range_run<CharT>::clear(range<CharT> const& r)
|
||||
{
|
||||
BOOST_SPIRIT_ASSERT(r.is_valid());
|
||||
if (!run.empty())
|
||||
{
|
||||
iterator iter =
|
||||
std::lower_bound(
|
||||
run.begin(), run.end(), r,
|
||||
range_compare<CharT>()
|
||||
);
|
||||
|
||||
iterator left_iter;
|
||||
|
||||
if ((iter != run.begin()) &&
|
||||
(left_iter = (iter - 1))->includes(r.first))
|
||||
{
|
||||
if (left_iter->last > r.last)
|
||||
{
|
||||
CharT save_last = left_iter->last;
|
||||
left_iter->last = r.first-1;
|
||||
run.insert(iter, range<CharT>(r.last+1, save_last));
|
||||
return;
|
||||
}
|
||||
else
|
||||
{
|
||||
left_iter->last = r.first-1;
|
||||
}
|
||||
}
|
||||
|
||||
iterator i = iter;
|
||||
while (i != run.end() && r.includes(*i))
|
||||
i++;
|
||||
if (i != run.end() && i->includes(r.last))
|
||||
i->first = r.last+1;
|
||||
run.erase(iter, i);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline void
|
||||
range_run<CharT>::clear()
|
||||
{ run.clear(); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline typename range_run<CharT>::const_iterator
|
||||
range_run<CharT>::begin() const
|
||||
{ return run.begin(); }
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline typename range_run<CharT>::const_iterator
|
||||
range_run<CharT>::end() const
|
||||
{ return run.end(); }
|
||||
|
||||
}} // namespace utility::impl
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,666 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Joel de Guzman
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_CHSET_OPERATORS_IPP
|
||||
#define BOOST_SPIRIT_CHSET_OPERATORS_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <boost/limits.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) |= b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) -= b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator~(chset<CharT> const& a)
|
||||
{
|
||||
return chset<CharT>(a).inverse();
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) &= b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) ^= b;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// range <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, range<CharT> const& b)
|
||||
{
|
||||
chset<CharT> a_(a);
|
||||
a_.set(b);
|
||||
return a_;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, range<CharT> const& b)
|
||||
{
|
||||
chset<CharT> a_(a);
|
||||
if(b.first != (std::numeric_limits<CharT>::min)()) {
|
||||
a_.clear(range<CharT>((std::numeric_limits<CharT>::min)(), b.first - 1));
|
||||
}
|
||||
if(b.last != (std::numeric_limits<CharT>::max)()) {
|
||||
a_.clear(range<CharT>(b.last + 1, (std::numeric_limits<CharT>::max)()));
|
||||
}
|
||||
return a_;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, range<CharT> const& b)
|
||||
{
|
||||
chset<CharT> a_(a);
|
||||
a_.clear(b);
|
||||
return a_;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, range<CharT> const& b)
|
||||
{
|
||||
return a ^ chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(range<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
chset<CharT> b_(b);
|
||||
b_.set(a);
|
||||
return b_;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(range<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
chset<CharT> b_(b);
|
||||
if(a.first != (std::numeric_limits<CharT>::min)()) {
|
||||
b_.clear(range<CharT>((std::numeric_limits<CharT>::min)(), a.first - 1));
|
||||
}
|
||||
if(a.last != (std::numeric_limits<CharT>::max)()) {
|
||||
b_.clear(range<CharT>(a.last + 1, (std::numeric_limits<CharT>::max)()));
|
||||
}
|
||||
return b_;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(range<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) - b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(range<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) ^ b;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// literal primitives <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, CharT b)
|
||||
{
|
||||
return a | chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, CharT b)
|
||||
{
|
||||
return a & chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, CharT b)
|
||||
{
|
||||
return a - chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, CharT b)
|
||||
{
|
||||
return a ^ chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(CharT a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) | b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(CharT a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) & b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(CharT a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) - b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(CharT a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) ^ b;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// chlit <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, chlit<CharT> const& b)
|
||||
{
|
||||
return a | chset<CharT>(b.ch);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, chlit<CharT> const& b)
|
||||
{
|
||||
return a & chset<CharT>(b.ch);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, chlit<CharT> const& b)
|
||||
{
|
||||
return a - chset<CharT>(b.ch);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, chlit<CharT> const& b)
|
||||
{
|
||||
return a ^ chset<CharT>(b.ch);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chlit<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a.ch) | b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chlit<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a.ch) & b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chlit<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a.ch) - b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chlit<CharT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a.ch) ^ b;
|
||||
}
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// negated_char_parser <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, negated_char_parser<ParserT> const& b)
|
||||
{
|
||||
return a | chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, negated_char_parser<ParserT> const& b)
|
||||
{
|
||||
return a & chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, negated_char_parser<ParserT> const& b)
|
||||
{
|
||||
return a - chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, negated_char_parser<ParserT> const& b)
|
||||
{
|
||||
return a ^ chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator|(negated_char_parser<ParserT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) | b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator&(negated_char_parser<ParserT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) & b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator-(negated_char_parser<ParserT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) - b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT, typename ParserT>
|
||||
inline chset<CharT>
|
||||
operator^(negated_char_parser<ParserT> const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) ^ b;
|
||||
}
|
||||
|
||||
#else // BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// negated_char_parser<range> <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, negated_char_parser<range<CharT> > const& b)
|
||||
{
|
||||
return a | chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, negated_char_parser<range<CharT> > const& b)
|
||||
{
|
||||
return a & chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, negated_char_parser<range<CharT> > const& b)
|
||||
{
|
||||
return a - chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, negated_char_parser<range<CharT> > const& b)
|
||||
{
|
||||
return a ^ chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(negated_char_parser<range<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) | b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(negated_char_parser<range<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) & b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(negated_char_parser<range<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) - b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(negated_char_parser<range<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) ^ b;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// negated_char_parser<chlit> <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, negated_char_parser<chlit<CharT> > const& b)
|
||||
{
|
||||
return a | chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, negated_char_parser<chlit<CharT> > const& b)
|
||||
{
|
||||
return a & chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, negated_char_parser<chlit<CharT> > const& b)
|
||||
{
|
||||
return a - chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, negated_char_parser<chlit<CharT> > const& b)
|
||||
{
|
||||
return a ^ chset<CharT>(b);
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(negated_char_parser<chlit<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) | b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(negated_char_parser<chlit<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) & b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(negated_char_parser<chlit<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) - b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(negated_char_parser<chlit<CharT> > const& a, chset<CharT> const& b)
|
||||
{
|
||||
return chset<CharT>(a) ^ b;
|
||||
}
|
||||
|
||||
#endif // BOOST_WORKAROUND(BOOST_MSVC, < 1300)
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// anychar_parser <--> chset free operators
|
||||
//
|
||||
// Where a is chset and b is a anychar_parser, and vice-versa, implements:
|
||||
//
|
||||
// a | b, a & b, a - b, a ^ b
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace impl {
|
||||
|
||||
template <typename CharT>
|
||||
inline BOOST_SPIRIT_CLASSIC_NS::range<CharT> const&
|
||||
full()
|
||||
{
|
||||
static BOOST_SPIRIT_CLASSIC_NS::range<CharT> full_(
|
||||
(std::numeric_limits<CharT>::min)(),
|
||||
(std::numeric_limits<CharT>::max)());
|
||||
return full_;
|
||||
}
|
||||
|
||||
template <typename CharT>
|
||||
inline BOOST_SPIRIT_CLASSIC_NS::range<CharT> const&
|
||||
empty()
|
||||
{
|
||||
static BOOST_SPIRIT_CLASSIC_NS::range<CharT> empty_;
|
||||
return empty_;
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const&, anychar_parser)
|
||||
{
|
||||
return chset<CharT>(impl::full<CharT>());
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& a, anychar_parser)
|
||||
{
|
||||
return a;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const&, anychar_parser)
|
||||
{
|
||||
return chset<CharT>();
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, anychar_parser)
|
||||
{
|
||||
return ~a;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(anychar_parser, chset<CharT> const& /*b*/)
|
||||
{
|
||||
return chset<CharT>(impl::full<CharT>());
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(anychar_parser, chset<CharT> const& b)
|
||||
{
|
||||
return b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(anychar_parser, chset<CharT> const& b)
|
||||
{
|
||||
return ~b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(anychar_parser, chset<CharT> const& b)
|
||||
{
|
||||
return ~b;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// nothing_parser <--> chset free operators implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(chset<CharT> const& a, nothing_parser)
|
||||
{
|
||||
return a;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(chset<CharT> const& /*a*/, nothing_parser)
|
||||
{
|
||||
return impl::empty<CharT>();
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(chset<CharT> const& a, nothing_parser)
|
||||
{
|
||||
return a;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(chset<CharT> const& a, nothing_parser)
|
||||
{
|
||||
return a;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator|(nothing_parser, chset<CharT> const& b)
|
||||
{
|
||||
return b;
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator&(nothing_parser, chset<CharT> const& /*b*/)
|
||||
{
|
||||
return impl::empty<CharT>();
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator-(nothing_parser, chset<CharT> const& /*b*/)
|
||||
{
|
||||
return impl::empty<CharT>();
|
||||
}
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
inline chset<CharT>
|
||||
operator^(nothing_parser, chset<CharT> const& b)
|
||||
{
|
||||
return b;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,221 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2002-2003 Hartmut Kaiser
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_CONFIX_IPP
|
||||
#define BOOST_SPIRIT_CONFIX_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <boost/spirit/home/classic/meta/refactoring.hpp>
|
||||
#include <boost/spirit/home/classic/core/composite/impl/directives.ipp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Types to distinguish nested and non-nested confix parsers
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
struct is_nested {};
|
||||
struct non_nested {};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Types to distinguish between confix parsers, which are implicitly lexems
|
||||
// and without this behaviour
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
struct is_lexeme {};
|
||||
struct non_lexeme {};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// confix_parser_type class implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace impl {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// implicitly insert a lexeme_d into the parsing process
|
||||
|
||||
template <typename LexemeT>
|
||||
struct select_confix_parse_lexeme;
|
||||
|
||||
template <>
|
||||
struct select_confix_parse_lexeme<is_lexeme> {
|
||||
|
||||
template <typename ParserT, typename ScannerT>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ParserT const& p, ScannerT const& scan)
|
||||
{
|
||||
typedef typename parser_result<ParserT, ScannerT>::type result_t;
|
||||
return contiguous_parser_parse<result_t>(p, scan, scan);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct select_confix_parse_lexeme<non_lexeme> {
|
||||
|
||||
template <typename ParserT, typename ScannerT>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ParserT const& p, ScannerT const& scan)
|
||||
{
|
||||
return p.parse(scan);
|
||||
}
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// parse confix sequences with refactoring
|
||||
|
||||
template <typename NestedT>
|
||||
struct select_confix_parse_refactor;
|
||||
|
||||
template <>
|
||||
struct select_confix_parse_refactor<is_nested> {
|
||||
|
||||
template <
|
||||
typename LexemeT, typename ParserT, typename ScannerT,
|
||||
typename OpenT, typename ExprT, typename CloseT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(
|
||||
LexemeT const &, ParserT const& this_, ScannerT const& scan,
|
||||
OpenT const& open, ExprT const& expr, CloseT const& close)
|
||||
{
|
||||
typedef refactor_action_gen<refactor_unary_gen<> > refactor_t;
|
||||
const refactor_t refactor_body_d = refactor_t(refactor_unary_d);
|
||||
|
||||
return select_confix_parse_lexeme<LexemeT>::parse((
|
||||
open
|
||||
>> (this_ | refactor_body_d[expr - close])
|
||||
>> close
|
||||
), scan);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct select_confix_parse_refactor<non_nested> {
|
||||
|
||||
template <
|
||||
typename LexemeT, typename ParserT, typename ScannerT,
|
||||
typename OpenT, typename ExprT, typename CloseT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(
|
||||
LexemeT const &, ParserT const& /*this_*/, ScannerT const& scan,
|
||||
OpenT const& open, ExprT const& expr, CloseT const& close)
|
||||
{
|
||||
typedef refactor_action_gen<refactor_unary_gen<> > refactor_t;
|
||||
const refactor_t refactor_body_d = refactor_t(refactor_unary_d);
|
||||
|
||||
return select_confix_parse_lexeme<LexemeT>::parse((
|
||||
open
|
||||
>> refactor_body_d[expr - close]
|
||||
>> close
|
||||
), scan);
|
||||
}
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// parse confix sequences without refactoring
|
||||
|
||||
template <typename NestedT>
|
||||
struct select_confix_parse_no_refactor;
|
||||
|
||||
template <>
|
||||
struct select_confix_parse_no_refactor<is_nested> {
|
||||
|
||||
template <
|
||||
typename LexemeT, typename ParserT, typename ScannerT,
|
||||
typename OpenT, typename ExprT, typename CloseT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(
|
||||
LexemeT const &, ParserT const& this_, ScannerT const& scan,
|
||||
OpenT const& open, ExprT const& expr, CloseT const& close)
|
||||
{
|
||||
return select_confix_parse_lexeme<LexemeT>::parse((
|
||||
open
|
||||
>> (this_ | (expr - close))
|
||||
>> close
|
||||
), scan);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct select_confix_parse_no_refactor<non_nested> {
|
||||
|
||||
template <
|
||||
typename LexemeT, typename ParserT, typename ScannerT,
|
||||
typename OpenT, typename ExprT, typename CloseT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(
|
||||
LexemeT const &, ParserT const & /*this_*/, ScannerT const& scan,
|
||||
OpenT const& open, ExprT const& expr, CloseT const& close)
|
||||
{
|
||||
return select_confix_parse_lexeme<LexemeT>::parse((
|
||||
open
|
||||
>> (expr - close)
|
||||
>> close
|
||||
), scan);
|
||||
}
|
||||
};
|
||||
|
||||
// the refactoring is handled by the refactoring parsers, so here there
|
||||
// is no need to pay attention to these issues.
|
||||
|
||||
template <typename CategoryT>
|
||||
struct confix_parser_type {
|
||||
|
||||
template <
|
||||
typename NestedT, typename LexemeT,
|
||||
typename ParserT, typename ScannerT,
|
||||
typename OpenT, typename ExprT, typename CloseT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(
|
||||
NestedT const &, LexemeT const &lexeme,
|
||||
ParserT const& this_, ScannerT const& scan,
|
||||
OpenT const& open, ExprT const& expr, CloseT const& close)
|
||||
{
|
||||
return select_confix_parse_refactor<NestedT>::
|
||||
parse(lexeme, this_, scan, open, expr, close);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct confix_parser_type<plain_parser_category> {
|
||||
|
||||
template <
|
||||
typename NestedT, typename LexemeT,
|
||||
typename ParserT, typename ScannerT,
|
||||
typename OpenT, typename ExprT, typename CloseT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(
|
||||
NestedT const &, LexemeT const &lexeme,
|
||||
ParserT const& this_, ScannerT const& scan,
|
||||
OpenT const& open, ExprT const& expr, CloseT const& close)
|
||||
{
|
||||
return select_confix_parse_no_refactor<NestedT>::
|
||||
parse(lexeme, this_, scan, open, expr, close);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace impl
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,224 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2001-2003 Daniel Nuffer
|
||||
Copyright (c) 2002-2003 Hartmut Kaiser
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_ESCAPE_CHAR_IPP
|
||||
#define BOOST_SPIRIT_ESCAPE_CHAR_IPP
|
||||
|
||||
#include <boost/spirit/home/classic/core/parser.hpp>
|
||||
#include <boost/spirit/home/classic/core/primitives/numerics.hpp>
|
||||
#include <boost/spirit/home/classic/core/composite/difference.hpp>
|
||||
#include <boost/spirit/home/classic/core/composite/sequence.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// escape_char_parser class
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
const unsigned long c_escapes = 1;
|
||||
const unsigned long lex_escapes = c_escapes << 1;
|
||||
|
||||
//////////////////////////////////
|
||||
namespace impl {
|
||||
|
||||
//////////////////////////////////
|
||||
#if (defined(BOOST_MSVC) && (BOOST_MSVC <= 1310))
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4127)
|
||||
#endif
|
||||
template <unsigned long Flags, typename CharT>
|
||||
struct escape_char_action_parse {
|
||||
|
||||
template <typename ParserT, typename ScannerT>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const &p)
|
||||
{
|
||||
// Actually decode the escape char.
|
||||
typedef CharT char_t;
|
||||
typedef typename ScannerT::iterator_t iterator_t;
|
||||
typedef typename parser_result<ParserT, ScannerT>::type result_t;
|
||||
|
||||
if (scan.first != scan.last) {
|
||||
|
||||
iterator_t save = scan.first;
|
||||
if (result_t hit = p.subject().parse(scan)) {
|
||||
|
||||
char_t unescaped;
|
||||
|
||||
scan.first = save;
|
||||
if (*scan.first == '\\') {
|
||||
|
||||
++scan.first;
|
||||
switch (*scan.first) {
|
||||
case 'b': unescaped = '\b'; ++scan.first; break;
|
||||
case 't': unescaped = '\t'; ++scan.first; break;
|
||||
case 'n': unescaped = '\n'; ++scan.first; break;
|
||||
case 'f': unescaped = '\f'; ++scan.first; break;
|
||||
case 'r': unescaped = '\r'; ++scan.first; break;
|
||||
case '"': unescaped = '"'; ++scan.first; break;
|
||||
case '\'': unescaped = '\''; ++scan.first; break;
|
||||
case '\\': unescaped = '\\'; ++scan.first; break;
|
||||
|
||||
case 'x': case 'X':
|
||||
{
|
||||
char_t hex = 0;
|
||||
char_t const lim =
|
||||
(std::numeric_limits<char_t>::max)() >> 4;
|
||||
|
||||
++scan.first;
|
||||
while (scan.first != scan.last)
|
||||
{
|
||||
char_t c = *scan.first;
|
||||
if (hex > lim && impl::isxdigit_(c))
|
||||
{
|
||||
// overflow detected
|
||||
scan.first = save;
|
||||
return scan.no_match();
|
||||
}
|
||||
if (impl::isdigit_(c))
|
||||
{
|
||||
hex <<= 4;
|
||||
hex |= c - '0';
|
||||
++scan.first;
|
||||
}
|
||||
else if (impl::isxdigit_(c))
|
||||
{
|
||||
hex <<= 4;
|
||||
c = impl::toupper_(c);
|
||||
hex |= c - 'A' + 0xA;
|
||||
++scan.first;
|
||||
}
|
||||
else
|
||||
{
|
||||
break; // reached the end of the number
|
||||
}
|
||||
}
|
||||
unescaped = hex;
|
||||
}
|
||||
break;
|
||||
|
||||
case '0': case '1': case '2': case '3':
|
||||
case '4': case '5': case '6': case '7':
|
||||
{
|
||||
char_t oct = 0;
|
||||
char_t const lim =
|
||||
(std::numeric_limits<char_t>::max)() >> 3;
|
||||
while (scan.first != scan.last)
|
||||
{
|
||||
char_t c = *scan.first;
|
||||
if (oct > lim && (c >= '0' && c <= '7'))
|
||||
{
|
||||
// overflow detected
|
||||
scan.first = save;
|
||||
return scan.no_match();
|
||||
}
|
||||
|
||||
if (c >= '0' && c <= '7')
|
||||
{
|
||||
oct <<= 3;
|
||||
oct |= c - '0';
|
||||
++scan.first;
|
||||
}
|
||||
else
|
||||
{
|
||||
break; // reached end of digits
|
||||
}
|
||||
}
|
||||
unescaped = oct;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
if (Flags & c_escapes)
|
||||
{
|
||||
// illegal C escape sequence
|
||||
scan.first = save;
|
||||
return scan.no_match();
|
||||
}
|
||||
else
|
||||
{
|
||||
unescaped = *scan.first;
|
||||
++scan.first;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
else {
|
||||
unescaped = *scan.first;
|
||||
++scan.first;
|
||||
}
|
||||
|
||||
scan.do_action(p.predicate(), unescaped, save, scan.first);
|
||||
return hit;
|
||||
}
|
||||
}
|
||||
return scan.no_match(); // overflow detected
|
||||
}
|
||||
};
|
||||
#if (defined(BOOST_MSVC) && (BOOST_MSVC <= 1310))
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CharT>
|
||||
struct escape_char_parse {
|
||||
|
||||
template <typename ScannerT, typename ParserT>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const &scan, ParserT const &/*p*/)
|
||||
{
|
||||
typedef
|
||||
uint_parser<CharT, 8, 1,
|
||||
std::numeric_limits<CharT>::digits / 3 + 1
|
||||
>
|
||||
oct_parser_t;
|
||||
typedef
|
||||
uint_parser<CharT, 16, 1,
|
||||
std::numeric_limits<CharT>::digits / 4 + 1
|
||||
>
|
||||
hex_parser_t;
|
||||
|
||||
typedef alternative<difference<anychar_parser, chlit<CharT> >,
|
||||
sequence<chlit<CharT>, alternative<alternative<oct_parser_t,
|
||||
sequence<inhibit_case<chlit<CharT> >, hex_parser_t > >,
|
||||
difference<difference<anychar_parser,
|
||||
inhibit_case<chlit<CharT> > >, oct_parser_t > > > >
|
||||
parser_t;
|
||||
|
||||
static parser_t p =
|
||||
( (anychar_p - chlit<CharT>(CharT('\\')))
|
||||
| (chlit<CharT>(CharT('\\')) >>
|
||||
( oct_parser_t()
|
||||
| as_lower_d[chlit<CharT>(CharT('x'))] >> hex_parser_t()
|
||||
| (anychar_p - as_lower_d[chlit<CharT>(CharT('x'))] - oct_parser_t())
|
||||
)
|
||||
));
|
||||
|
||||
BOOST_SPIRIT_DEBUG_TRACE_NODE(p,
|
||||
(BOOST_SPIRIT_DEBUG_FLAGS & BOOST_SPIRIT_DEBUG_FLAGS_ESCAPE_CHAR) != 0);
|
||||
|
||||
return p.parse(scan);
|
||||
}
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
} // namespace impl
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,168 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2002-2003 Hartmut Kaiser
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_LISTS_IPP
|
||||
#define BOOST_SPIRIT_LISTS_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <boost/spirit/home/classic/meta/refactoring.hpp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// list_parser_type class implementation
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
struct no_list_endtoken { typedef no_list_endtoken embed_t; };
|
||||
|
||||
namespace impl {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Refactor the original list item parser
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// match list with 'extended' syntax
|
||||
template <typename EndT>
|
||||
struct select_list_parse_refactor {
|
||||
|
||||
template <
|
||||
typename ParserT, typename ScannerT,
|
||||
typename ItemT, typename DelimT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const& /*p*/,
|
||||
ItemT const &item, DelimT const &delim, EndT const &end)
|
||||
{
|
||||
typedef refactor_action_gen<refactor_unary_gen<> > refactor_t;
|
||||
const refactor_t refactor_item_d = refactor_t(refactor_unary_d);
|
||||
|
||||
return (
|
||||
refactor_item_d[item - (end | delim)]
|
||||
>> *(delim >> refactor_item_d[item - (end | delim)])
|
||||
>> !(delim >> end)
|
||||
).parse(scan);
|
||||
}
|
||||
};
|
||||
|
||||
// match list with 'normal' syntax (without an 'end' parser)
|
||||
template <>
|
||||
struct select_list_parse_refactor<no_list_endtoken> {
|
||||
|
||||
template <
|
||||
typename ParserT, typename ScannerT,
|
||||
typename ItemT, typename DelimT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const& /*p*/,
|
||||
ItemT const &item, DelimT const &delim, no_list_endtoken const&)
|
||||
{
|
||||
typedef refactor_action_gen<refactor_unary_gen<> > refactor_t;
|
||||
const refactor_t refactor_item_d = refactor_t(refactor_unary_d);
|
||||
|
||||
return (
|
||||
refactor_item_d[item - delim]
|
||||
>> *(delim >> refactor_item_d[item - delim])
|
||||
).parse(scan);
|
||||
}
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Do not refactor the original list item parser.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// match list with 'extended' syntax
|
||||
template <typename EndT>
|
||||
struct select_list_parse_no_refactor {
|
||||
|
||||
template <
|
||||
typename ParserT, typename ScannerT,
|
||||
typename ItemT, typename DelimT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const& /*p*/,
|
||||
ItemT const &item, DelimT const &delim, EndT const &end)
|
||||
{
|
||||
return (
|
||||
(item - (end | delim))
|
||||
>> *(delim >> (item - (end | delim)))
|
||||
>> !(delim >> end)
|
||||
).parse(scan);
|
||||
}
|
||||
};
|
||||
|
||||
// match list with 'normal' syntax (without an 'end' parser)
|
||||
template <>
|
||||
struct select_list_parse_no_refactor<no_list_endtoken> {
|
||||
|
||||
template <
|
||||
typename ParserT, typename ScannerT,
|
||||
typename ItemT, typename DelimT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const& /*p*/,
|
||||
ItemT const &item, DelimT const &delim, no_list_endtoken const&)
|
||||
{
|
||||
return (
|
||||
(item - delim)
|
||||
>> *(delim >> (item - delim))
|
||||
).parse(scan);
|
||||
}
|
||||
};
|
||||
|
||||
// the refactoring is handled by the refactoring parsers, so here there
|
||||
// is no need to pay attention to these issues.
|
||||
|
||||
template <typename CategoryT>
|
||||
struct list_parser_type {
|
||||
|
||||
template <
|
||||
typename ParserT, typename ScannerT,
|
||||
typename ItemT, typename DelimT, typename EndT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const& p,
|
||||
ItemT const &item, DelimT const &delim, EndT const &end)
|
||||
{
|
||||
return select_list_parse_refactor<EndT>::
|
||||
parse(scan, p, item, delim, end);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct list_parser_type<plain_parser_category> {
|
||||
|
||||
template <
|
||||
typename ParserT, typename ScannerT,
|
||||
typename ItemT, typename DelimT, typename EndT
|
||||
>
|
||||
static typename parser_result<ParserT, ScannerT>::type
|
||||
parse(ScannerT const& scan, ParserT const& p,
|
||||
ItemT const &item, DelimT const &delim, EndT const &end)
|
||||
{
|
||||
return select_list_parse_no_refactor<EndT>::
|
||||
parse(scan, p, item, delim, end);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace impl
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
/*=============================================================================
|
||||
Copyright (c) 2002-2003 Hartmut Kaiser
|
||||
http://spirit.sourceforge.net/
|
||||
|
||||
Use, modification and distribution is subject to the Boost Software
|
||||
License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
=============================================================================*/
|
||||
#ifndef BOOST_SPIRIT_REGEX_IPP
|
||||
#define BOOST_SPIRIT_REGEX_IPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include <boost/spirit/home/classic/core/primitives/impl/primitives.ipp>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost { namespace spirit {
|
||||
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
|
||||
|
||||
namespace impl {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
inline const char* rx_prefix(char) { return "\\A"; }
|
||||
inline const wchar_t* rx_prefix(wchar_t) { return L"\\A"; }
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// rx_parser class
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CharT = char>
|
||||
class rx_parser : public parser<rx_parser<CharT> > {
|
||||
|
||||
public:
|
||||
typedef std::basic_string<CharT> string_t;
|
||||
typedef rx_parser<CharT> self_t;
|
||||
|
||||
rx_parser(CharT const *first, CharT const *last)
|
||||
{
|
||||
rxstr = string_t(rx_prefix(CharT())) + string_t(first, last);
|
||||
}
|
||||
|
||||
rx_parser(CharT const *first)
|
||||
{
|
||||
rxstr = string_t(rx_prefix(CharT())) +
|
||||
string_t(first, impl::get_last(first));
|
||||
}
|
||||
|
||||
template <typename ScannerT>
|
||||
typename parser_result<self_t, ScannerT>::type
|
||||
parse(ScannerT const& scan) const
|
||||
{
|
||||
boost::match_results<typename ScannerT::iterator_t> what;
|
||||
boost::regex_search(scan.first, scan.last, what, rxstr,
|
||||
boost::match_default);
|
||||
|
||||
if (!what[0].matched)
|
||||
return scan.no_match();
|
||||
|
||||
scan.first = what[0].second;
|
||||
return scan.create_match(what[0].length(), nil_t(),
|
||||
what[0].first, scan.first);
|
||||
}
|
||||
|
||||
private:
|
||||
#if BOOST_VERSION >= 013300
|
||||
boost::basic_regex<CharT> rxstr; // regular expression to match
|
||||
#else
|
||||
boost::reg_expression<CharT> rxstr; // regular expression to match
|
||||
#endif
|
||||
};
|
||||
|
||||
} // namespace impl
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
BOOST_SPIRIT_CLASSIC_NAMESPACE_END
|
||||
|
||||
}} // namespace boost::spirit
|
||||
|
||||
#endif // BOOST_SPIRIT_REGEX_IPP
|
||||
Reference in New Issue
Block a user