I'm using clang 9.0.1 and gcc 9.2.1 on x64 Linux, both with --std=c++17
(or --std=c++2a
).
Gcc can build the following example without any error or warning, while clang++ reports error: constexpr if condition is not a constant expression
on both if constexpr
lines. (btw, on my MacBook, Apple clang-11.0.0 reports the same error too.)
MCVE:
#include <utility>
enum class TopicType {
MarketData = 'M',
Timer = 'T',
};
template<class Topic>
struct TopicBase {
constexpr static TopicType type() { return Topic::type; };
const Topic& topicImp;
explicit TopicBase(const Topic &t) : topicImp(t) {}
};
struct MarketDataTopic {
static constexpr TopicType type{TopicType::MarketData};
};
struct TimerTopic {
static constexpr TopicType type{TopicType::Timer};
};
template<class Topic>
int subscribe(TopicBase<Topic>&& topic) {
if constexpr (topic.type() == TopicType::MarketData) { // <-- clang++ reports error here
return 1;
}
if constexpr (topic.type() == TopicType::Timer) { // and error here
return 2;
}
return -1;
}
int main(int argc, const char **argv) {
MarketDataTopic m{};
TimerTopic t{};
TopicBase<MarketDataTopic> b1{m};
TopicBase<TimerTopic> b2{t};
subscribe(std::move(b1));
return 0;
}
Online compiler https://godbolt.org/z/rARi_N has the same result.
So which compiler is right about this? And if it is an error, how to fix it for clang?
Well you can do this to make it work for clang:
template<class Topic>
int subscribe(TopicBase<Topic>&& topic) {
using myType = TopicBase<Topic>;
if constexpr (myType::type() == TopicType::MarketData) { // <-- clang++ reports error here
return 1;
}
if constexpr (myType::type() == TopicType::Timer) { // and error here
return 2;
}
return -1;
}
Run live
Most probably that's a bug in clang. Better report it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With