I have an interesting issue on the MSVC v19.28 compiler (later versions fix this problem) where a const char* being passed to a variadic template class fails to resolve correctly. If the const char* is passed to a variadic template function then there are no errors.
Here's the code for clarity:
#include <type_traits>
template <typename... T_Args>
struct Foo
{
template <typename T_Func>
void foo(T_Func func, T_Args&&... args)
{
func(std::forward<T_Args>(args)...);
}
};
template <typename T_Func, typename... T_Args>
void bar(T_Func func, T_Args&&... args)
{
func(std::forward<T_Args>(args)...);
}
int main()
{
bar([](int, float, const char* c){ }, 5, 5.0f, "Hello world");
// <source>(26): error C2672: 'Foo<int,float,const char *>::foo': no matching overloaded function found
// <source>(26): error C2440: 'initializing': cannot convert from 'const char [12]' to 'const char *&&'
// <source>(26): note: You cannot bind an lvalue to an rvalue reference
Foo<int, float, const char*> f;
f.foo([](int, float, const char* c){ }, 5, 5.0f, "Hello world");
// this compiles, but what are the repurcussions of std::move() on a string literal?
Foo<int, float, const char*> g;
g.foo([](int, float, const char* c){ }, 5, 5.0f, std::move("Hello world"));
}
Since I work on a large team, I am unable to recommend upgrading the toolchain/compiler and so I am looking for workarounds until the compiler can be updated.
One of the workaround is to use std::move("Hello world"). What is std::move doing do a const char* and what the potential side-effects?