I want to check if a constexpr number is in a constexpr array at compile time. If not, stop compiling. My ideographic example:
constexpr void PinValid(uint8_t Pin)
{
constexpr uint8_t ValidPins[] = {2, 3, 18, 19, 20, 21};
for (uint8_t P : ValidPins)
if (Pin == P)
return;
static_assert(false);
}
This code fails for any given Pin even if it is in the ValidPins.
CodePudding user response:
You can write like this:
constexpr bool PinValid(uint8_t Pin)
{
constexpr uint8_t ValidPins[] = {2, 3, 18, 19, 20, 21};
for (uint8_t P : ValidPins)
if (Pin == P)
return true;
return false;
}
static_assert(PinValid(3));
CodePudding user response:
I'd like to add the following solution, even if the quality of the error message isn't as good as in the example in the other answer, on some compilers.
In c 20 you can throw an exception in a constexpr function which will result in a compilation error if it gets thrown at compile-time:
#include <cstdint>
#include <array>
#include <stdexcept>
consteval void PinValid(uint8_t Pin)
{
constexpr uint8_t ValidPins[] = {2, 3, 18, 19, 20, 21};
for (uint8_t P : ValidPins)
if (Pin == P)
return;
throw std::invalid_argument("not a valid pin");
}
int main() {
PinValid(20);
PinValid(5); // Does not compile
}
See the example on Compiler Explorer. Notice that it currently doesn't work on clang, though