How to prevent such code from compiling?
#include
#include
#include
#include
int main() {
std::
You could start writing a wrapper for your integral types to match the exact type (or some conditions).
#include
#include
#include
#include
#include
template struct conjunction : std::true_type {};
template struct conjunction : B1 {};
template
struct conjunction
: std::conditional_t, B1> {};
template struct int_wrapper {
explicit int_wrapper() : _val{T{}} {}
explicit int_wrapper(const int_wrapper &other) : _val{other._val} {}
template explicit int_wrapper(U val) : _val{val} {
static_assert(sizeof(T) >= sizeof(U), "Size mismatch.");
static_assert(conjunction, std::is_signed>::value,
"sign mismatch");
}
explicit operator T() { return _val; }
explicit operator T() const { return _val; }
T _val;
};
std::ostream &operator<<(std::ostream &stream, const int_wrapper &v) {
stream << v._val;
return stream;
}
int main() {
std::vector> v;
v.emplace_back(std::numeric_limits::max());
std::cout << v.back() << std::endl;
return 0;
}
clang on macOS gives you error like:
so.cpp:18:60: error: non-constant-expression cannot be narrowed from type 'unsigned long long' to 'short' in initializer list
[-Wc++11-narrowing]
template explicit int_wrapper(U val) : _val{val} {
^~~
/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/memory:1752:31: note: in
instantiation of function template specialization 'int_wrapper::int_wrapper' requested here
::new((void*)__p) _Up(_VSTD::forward<_Args>(__args)...);
^
/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/memory:1668:18: note: in
instantiation of function template specialization 'std::__1::allocator >::construct,
unsigned long long>' requested here
{__a.construct(__p, _VSTD::forward<_Args>(__args)...);}
^
/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/memory:1514:14: note: in
instantiation of function template specialization 'std::__1::allocator_traits >
>::__construct, unsigned long long>' requested here
{__construct(__has_construct(),
^
/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/vector:1643:25: note: in
instantiation of function template specialization 'std::__1::allocator_traits >
>::construct, unsigned long long>' requested here
__alloc_traits::construct(this->__alloc(),
^
so.cpp:37:5: note: in instantiation of function template specialization 'std::__1::vector,
std::__1::allocator > >::emplace_back' requested here
v.emplace_back(std::numeric_limits::max());
^
so.cpp:18:60: note: insert an explicit cast to silence this issue
template explicit int_wrapper(U val) : _val{val} {
^~~
static_cast( )
so.cpp:19:5: error: static_assert failed "Not the same size."
static_assert(sizeof(T) >= sizeof(U), "Not the same size.");
^ ~~~~~~~~~~~~~~~~~~~~~~
so.cpp:20:5: error: static_assert failed "sign mismatch"
static_assert(conjunction, std::is_signed>::value,
^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3 errors generated.