This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of New status.

### 3204. `sub_match::swap` only swaps the base class

Section: 32.8 [re.submatch] Status: New Submitter: Jonathan Wakely Opened: 2019-05-07 Last modified: 2022-11-06

Priority: 3

View other active issues in [re.submatch].

View all other issues in [re.submatch].

View all issues with New status.

Discussion:

`sub_match<I>` derives publicly from `pair<I,I>`, and so inherits `pair::swap(pair&)`. This means that the following program fails:

>     #include <regex>
>     #include <cassert>

>     int main()
>     {
>       std::sub_match<const char*> a, b;
>       a.matched = true;
>       a.swap(b);
>       assert(b.matched);
>     }

The `pair::swap(pair&)` member should be hidden by a `sub_match::swap(sub_match&)` member that does the right thing.

[2019-06-12 Priority set to 3 after reflector discussion]

[2020-05-01; Daniel adjusts wording to recent working draft]

[2022-04-25; Daniel adjusts wording to recent working draft]

In addition the revised wording uses the new standard phrase "The exception specification is equivalent to"

Previous resolution [SUPERSEDED]:

> This wording is relative to N4910.

> 1. Modify 32.8 [re.submatch], class template `sub_match` synopsis, as indicated:

>    >     template<class BidirectionalIterator>
>    >     class sub_match : public pair<BidirectionalIterator, BidirectionalIterator> {
>    >     public:
>    >       […]
>    >       int compare(const sub_match& s) const;
>    >       int compare(const string_type& s) const;
>    >       int compare(const value_type* s) const;

>    >       void swap(sub_match& s) noexcept(see below);
>    >     };

> 2. Modify 32.8.2 [re.submatch.members] as indicated:

>    >     int compare(const value_type* s) const;

>    > > […]

>    >     void swap(sub_match& s) noexcept(see below);

>    > > [Drafting note: The swappable requirement should really be unnecessary because Cpp17Iterator requires it, but there is no wording that requires `BidirectionalIterator` in Clause 32 [re] in general meets the bidirectional iterator requirements. Note that the definition found in 27.2 [algorithms.requirements] does not extend to 32 [re] normatively. — end drafting note]

>    > > -?- Preconditions: Lvalues of type `BidirectionalIterator` are swappable (16.4.4.3 [swappable.requirements]).

>    > > -?- Effects: Equivalent to:

>    > > >     this->pair<BidirectionalIterator, BidirectionalIterator>::swap(s);
>    > > >     std::swap(matched, s.matched);

>    > > -?- Remarks: The exception specification is equivalent to `is_nothrow_swappable_v<BidirectionalIterator>`.

[2022-11-06; Daniel comments and improves wording]

With the informal acceptance of P2696R0 by LWG during a pre-Kona telecon, we should use the new requirement set Cpp17Swappable instead of the "LValues are swappable" requirements.

Proposed resolution:

This wording is relative to N4917 and assumes the acceptance of P2696R0.

1. Modify 32.8 [re.submatch], class template `sub_match` synopsis, as indicated:

   >     template<class BidirectionalIterator>
   >     class sub_match : public pair<BidirectionalIterator, BidirectionalIterator> {
   >     public:
   >       […]
   >       int compare(const sub_match& s) const;
   >       int compare(const string_type& s) const;
   >       int compare(const value_type* s) const;

   >       void swap(sub_match& s) noexcept(see below);
   >     };

2. Modify 32.8.2 [re.submatch.members] as indicated:

   >     int compare(const value_type* s) const;

   > > […]

   >     void swap(sub_match& s) noexcept(see below);

   > > [Drafting note: The Cpp17Swappable requirement should really be unnecessary because Cpp17Iterator requires it, but there is no wording that requires `BidirectionalIterator` in Clause 32 [re] in general meets the bidirectional iterator requirements. Note that the definition found in 27.2 [algorithms.requirements] does not extend to 32 [re] normatively. — end drafting note]

   > > -?- Preconditions: `BidirectionalIterator` meets the Cpp17Swappable requirements (16.4.4.3 [swappable.requirements]).

   > > -?- Effects: Equivalent to:

   > > >     this->pair<BidirectionalIterator, BidirectionalIterator>::swap(s);
   > > >     std::swap(matched, s.matched);

   > > -?- Remarks: The exception specification is equivalent to `is_nothrow_swappable_v<BidirectionalIterator>`.