Skip to content

<regex>: Error C2664 in std::regex_traits::transform #1004

@AlexGuteniev

Description

@AlexGuteniev

Describe the bug
std::regex_traits::transform tries to use const _Elem* as internal iterator instead of user-defined iterator.

Command-line test case

d:\Temp2>type repro.cpp
#include <regex>
#include <iostream>

template <class It>
class forward_iterator
{
    It it_;

    template <class U> friend class forward_iterator;
public:
    typedef          std::forward_iterator_tag                 iterator_category;
    typedef typename std::iterator_traits<It>::value_type      value_type;
    typedef typename std::iterator_traits<It>::difference_type difference_type;
    typedef It                                                 pointer;
    typedef typename std::iterator_traits<It>::reference       reference;

    It base() const { return it_; }

    forward_iterator() : it_() {}
    explicit forward_iterator(It it) : it_(it) {}
    template <class U>
    forward_iterator(const forward_iterator<U>& u) : it_(u.it_) {}

    reference operator*() const { return *it_; }
    pointer operator->() const { return it_; }

    forward_iterator& operator++() { ++it_; return *this; }
    forward_iterator operator++(int)
    {
        forward_iterator tmp(*this); ++(*this); return tmp;
    }

    friend bool operator==(const forward_iterator& x, const forward_iterator& y)
    {
        return x.it_ == y.it_;
    }
    friend bool operator!=(const forward_iterator& x, const forward_iterator& y)
    {
        return !(x == y);
    }

    template <class T>
    void operator,(T const &) = delete;
};

int main()
{
    std::regex_traits<char> t;
    const char a[] = "a";
    const char B[] = "B";
    typedef forward_iterator<const char*> F;
    bool r = t.transform(F(a), F(a + 1)) > t.transform(F(B), F(B + 1));
    (void) r;
}

d:\Temp2>cl /EHsc /W4 .\repro.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 19.27.29009.1 for x86
Copyright (C) Microsoft Corporation.  All rights reserved.

repro.cpp
c:\Program Files (x86)\Microsoft Visual Studio\2019\Preview\VC\Tools\MSVC\14.27.29009\include\regex(283): error C2664: 'std::basic_string<char,std::char_traits<char>,std::allocator<char>> std::collate<_Elem>::transform(const _Elem *,const _Elem *) const': cannot convert argument 1 from '_FwdIt' to 'const _Elem *'
        with
        [
            _Elem=char
        ]
        and
        [
            _FwdIt=F
        ]
        and
        [
            _Elem=char
        ]
c:\Program Files (x86)\Microsoft Visual Studio\2019\Preview\VC\Tools\MSVC\14.27.29009\include\regex(283): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
c:\Program Files (x86)\Microsoft Visual Studio\2019\Preview\VC\Tools\MSVC\14.27.29009\include\locale(41): note: see declaration of 'std::collate<_Elem>::transform'
        with
        [
            _Elem=char
        ]
.\repro.cpp(52): note: see reference to function template instantiation 'std::basic_string<char,std::char_traits<char>,std::allocator<char>> std::_Regex_traits<char>::transform<F>(_FwdIt,_FwdIt) const' being compiled
        with
        [
            _FwdIt=F
        ]
.\repro.cpp(52): note: see reference to function template instantiation 'std::basic_string<char,std::char_traits<char>,std::allocator<char>> std::_Regex_traits<char>::transform<F>(_FwdIt,_FwdIt) const' being compiled
        with
        [
            _FwdIt=F
        ]

Expected behavior
The program should compile

STL version

Microsoft Visual Studio Professional 2019 Preview
Version 16.7.0 Preview 3.1

Additional context
The following is the equivalent of the repro:

# STL bug: regex_traits::transform() isn't following the Standard.
std/re/re.traits/transform.pass.cpp FAIL

Also tracked by DevCom-1076807 and Microsoft-internal VSO-1142061 / AB#1142061.

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't workingfixedSomething works now, yay!

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions