0

I have code that looks like this:

enum class MyTypes {
   TYPE_1 = 1,
   TYPE_2 = 2,
   TYPE_3 = 3
};

static const std::regex reg1("some unique expression");
static const std::regex reg2("some unique expression");
static const std::regex reg3("some unique expression");

static const std::map<MyTypes, std::regex> ValidSets = {
    {MyTypes::TYPE_1, reg1},
    {MyTypes::TYPE_2, reg2},
    {MyTypes::TYPE_3, reg3}
};

static const auto match = [&](const std::string& str, const std::regex& reg) -> bool {
    std::smatch base_match;
    return std::regex_match(str, base_match, reg);
};

template<MyTypes TYPE = MyTypes::TYPE_2> // defaulting to a specific type
class Foo {
    std::string sequence_{""};
public:
    const std::uint16_t Type = static_cast<uint16_t>(TYPE);         

    Foo() = default;
    Foo(const std::string_view sequence) {
        assert(!sequence.empty() && "invalid input, must contain at least 1 character.");
        // Fails to compile
        assert(match(sequence.data(), ValidSets[TYPE]) && "invalid sequence set for this type."); 
        // Works
        assert(match(sequence.data(), ValidSets.at(TYPE)) && "invalid sequence set for this type.");
        sequence_ = sequence;
    }
};

Then I'll be trying to use it as such:

int main() {
    Foo bar_d("some character sequence"); // must match the regex for the default type

    Foo<Type::TYPE1> bar_1("some character sequence"); // must match the regex for type 1
    Foo<Type::TYPE3> bar_3("some character sequence"); // must match the regex for type 3
 
    return 0;
}

However, ValidSets[TYPE] is failing to compile within Visual Studio 2017 compiler error C2678. Yet when I change it to use ValidSets.at(TYPE) it compiles and executes just fine...

Why does one fail to compile and the other work?

10
  • 3
    Because the map is const, and [] is a non-const method. Commented Aug 19, 2020 at 21:38
  • 1
    Well, I did know that, but I just pasted the code into godbolt, and the compiler told me :) Commented Aug 19, 2020 at 21:40
  • 1
    @cigien thank you for the reminder and for the clarity! Commented Aug 19, 2020 at 21:42
  • 2
    BTW, it's irrelevant for this question now, but in the future make sure at least one of your tags is c++. You'll get a lot more eyes on the question that way. Commented Aug 19, 2020 at 21:45
  • 1
    dont confuse [] to be simple element access. This is what you get with at. [] does something different: It inserts a value in the map if not present and then returns a reference Commented Aug 19, 2020 at 21:54

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.