예제 #1
0
 void intersect_negated (basic_string_token &rhs_,
     basic_string_token &overlap_)
 {
     if (rhs_.any ())
     {
         overlap_._negated = true;
         overlap_._charset = _charset;
         rhs_._negated = false;
         rhs_._charset = _charset;
         clear ();
     }
     else // rhs._negated == false
     {
         rhs_.intersect_charset (*this, overlap_);
     }
 }
예제 #2
0
    void adjust(const range &range_, basic_string_token &token_,
        typename range_vector::iterator &iter_,
        typename range_vector::const_iterator &end_)
    {
        if (range_.first > iter_->first)
        {
            const index_type second_ = iter_->second;

            iter_->second = range_.first - 1;

            if (range_.second < second_)
            {
                range new_range_(range_.second + 1, second_);

                iter_ = token_.insert(new_range_);
                end_ = token_._ranges.end();
            }
        }
        else if (range_.second < iter_->second)
        {
            iter_->first = range_.second + 1;
        }
        else
        {
            iter_ = token_._ranges.erase(iter_);
            end_ = token_._ranges.end();
        }
    }
예제 #3
0
    void merge_diff_types (const basic_string_token &rhs_,
        basic_string_token &merged_) const
    {
        if (_negated)
        {
            merge_negated (*this, rhs_, merged_);
        }
        else
        {
            merge_negated (rhs_, *this, merged_);
        }

        merged_.normalise ();
    }
예제 #4
0
    void intersect(basic_string_token &rhs_, basic_string_token &overlap_)
    {
        typename range_vector::iterator lhs_iter_ = _ranges.begin();
        typename range_vector::const_iterator lhs_end_ = _ranges.end();
        typename range_vector::iterator rhs_iter_ = rhs_._ranges.begin();
        typename range_vector::const_iterator rhs_end_ = rhs_._ranges.end();

        while (lhs_iter_ != lhs_end_ && rhs_iter_ != rhs_end_)
        {
            if (rhs_iter_->first > lhs_iter_->second)
            {
                ++lhs_iter_;
            }
            else if (rhs_iter_->second < lhs_iter_->first)
            {
                ++rhs_iter_;
            }
            else
            {
                range range_;

                if (rhs_iter_->first > lhs_iter_->first)
                {
                    range_.first = rhs_iter_->first;
                }
                else
                {
                    range_.first = lhs_iter_->first;
                }

                if (rhs_iter_->second < lhs_iter_->second)
                {
                    range_.second = rhs_iter_->second;
                }
                else
                {
                    range_.second = lhs_iter_->second;
                }

                adjust(range_, *this, lhs_iter_, lhs_end_);
                adjust(range_, rhs_, rhs_iter_, rhs_end_);
                overlap_.insert(range_);
            }
        }
    }
예제 #5
0
    void intersect_charset (basic_string_token &rhs_,
        basic_string_token &overlap_)
    {
        if (rhs_.any ())
        {
            overlap_._charset = _charset;
            rhs_._negated = true;
            rhs_._charset = _charset;
            clear ();
        }
        else // rhs_._negated == true
        {
            typename string::iterator iter_ = _charset.begin ();
            typename string::iterator end_ = _charset.end ();
            typename string::iterator rhs_iter_ = rhs_._charset.begin ();
            typename string::iterator rhs_end_ = rhs_._charset.end ();

            while (iter_ != end_ && rhs_iter_ != rhs_end_)
            {
                if (*iter_ < *rhs_iter_)
                {
                    overlap_._charset += *iter_;
                    rhs_iter_ = rhs_._charset.insert (rhs_iter_, *iter_);
                    ++rhs_iter_;
                    rhs_end_ = rhs_._charset.end ();
                    iter_ = _charset.erase (iter_);
                    end_ = _charset.end ();
                }
                else if (*iter_ > *rhs_iter_)
                {
                    ++rhs_iter_;
                }
                else
                {
                    ++iter_;
                    ++rhs_iter_;
                }
            }

            if (iter_ != end_)
            {
                // nothing bigger in rhs_ than iter_,
                // so safe to merge using std lib.
                string temp_ (iter_, end_);

                // src, dest
                merge (temp_, overlap_._charset);
                _charset.erase (iter_, end_);
            }

            if (!overlap_._charset.empty ())
            {
                merge (overlap_._charset, rhs_._charset);
                // possible duplicates, so check for any and erase.
                rhs_._charset.erase (std::unique (rhs_._charset.begin (),
                    rhs_._charset.end ()), rhs_._charset.end ());
                normalise ();
                overlap_.normalise ();
                rhs_.normalise ();
            }
        }
    }
예제 #6
0
    void intersect_same_types (basic_string_token &rhs_, basic_string_token &overlap_)
    {
        if (any ())
        {
            clear ();
            overlap_._negated = true;
            rhs_.clear ();
        }
        else
        {
            typename string::iterator iter_ = _charset.begin ();
            typename string::iterator end_ = _charset.end ();
            typename string::iterator rhs_iter_ = rhs_._charset.begin ();
            typename string::iterator rhs_end_ = rhs_._charset.end ();

            overlap_._negated = _negated;

            while (iter_ != end_ && rhs_iter_ != rhs_end_)
            {
                if (*iter_ < *rhs_iter_)
                {
                    ++iter_;
                }
                else if (*iter_ > *rhs_iter_)
                {
                    ++rhs_iter_;
                }
                else
                {
                    overlap_._charset += *iter_;
                    iter_ = _charset.erase (iter_);
                    end_ = _charset.end ();
                    rhs_iter_ = rhs_._charset.erase (rhs_iter_);
                    rhs_end_ = rhs_._charset.end ();
                }
            }

            if (_negated)
            {
                // duplicates already merged, so safe to merge
                // using std lib.

                // src, dest
                merge (_charset, overlap_._charset);
                // duplicates already merged, so safe to merge
                // using std lib.

                // src, dest
                merge (rhs_._charset, overlap_._charset);
                _negated = false;
                rhs_._negated = false;
                std::swap (_charset, rhs_._charset);
                normalise ();
                overlap_.normalise ();
                rhs_.normalise ();
            }
            else if (!overlap_._charset.empty ())
            {
                normalise ();
                overlap_.normalise ();
                rhs_.normalise ();
            }
        }
    }
예제 #7
0
    void merge_same_types (const basic_string_token &rhs_,
        basic_string_token &merged_) const
    {
        if (any ())
        {
            merged_._negated = true;
        }
        else if (_negated)
        {
            typename string::const_iterator iter_ = _chars.begin ();
            typename string::const_iterator end_ = _chars.end ();
            typename string::const_iterator rhs_iter_ = rhs_._chars.begin ();
            typename string::const_iterator rhs_end_ = rhs_._chars.end ();

            merged_._negated = _negated;

            while (iter_ != end_ && rhs_iter_ != rhs_end_)
            {
                if (*iter_ < *rhs_iter_)
                {
                    ++iter_;
                }
                else if (*iter_ > *rhs_iter_)
                {
                    ++rhs_iter_;
                }
                else
                {
                    merged_._chars += *iter_;
                    ++iter_;
                    ++rhs_iter_;
                }
            }

            merged_.normalise ();
        }
        else
        {
            typename string::const_iterator iter_ = _chars.begin ();
            typename string::const_iterator end_ = _chars.end ();
            typename string::const_iterator rhs_iter_ = rhs_._chars.begin ();
            typename string::const_iterator rhs_end_ = rhs_._chars.end ();

            while (iter_ != end_ && rhs_iter_ != rhs_end_)
            {
                if (*iter_ < *rhs_iter_)
                {
                    merged_._chars += *iter_;
                    ++iter_;
                }
                else if (*iter_ > *rhs_iter_)
                {
                    merged_._chars += *rhs_iter_;
                    ++rhs_iter_;
                }
                else
                {
                    merged_._chars += *iter_;
                    ++iter_;
                    ++rhs_iter_;
                }
            }

            // Include any trailing chars
            if (iter_ != end_)
            {
                string temp_ (iter_, end_);

                merged_._chars += temp_;
            }
            else if (rhs_iter_ != rhs_end_)
            {
                string temp_ (rhs_iter_, rhs_end_);

                merged_._chars += temp_;
            }

            merged_.normalise ();
        }
    }