As far as I know, I cannot declare an rvalue reference to void
.
As an example, the following code is ill-formed:
void f(void &&v) { }
From [20.2.6/1] (function template declval) we have a declaration for declval
that is:
template <class T>
add_rvalue_reference_t<T>
declval() noexcept;
Thus, declval<void>
(let me say) would result in void &&
, that I guessed it was ill-formed as well as in the previous example.
Anyway, the following minimal, working example compiles:
#include<utility>
int main() {
decltype(std::declval<void>())* ptr = nullptr;
}
Note that the following is true too:
static_assert(std::is_same<decltype(std::declval<void>()), void>::value, "!");
I would have expected it to be void&&
as previously mentioned (or better, I was expecting it fails to compile).
Actually, it happens to be an rvalue reference for any other non-reference type.
As an example:
static_assert(std::is_same<decltype(std::declval<int>()), int&&>::value, "!");
Is declval<void>
a valid expression or not? Is the code above legal?
Why does the behavior in case of void
is different than with any other type? (For it wouldn't have worked otherwise could be an answer, if the code is legal).
If it's legal, where does the standard allow that? I've not been able to find the case.
Of course, the standard says:
The template parameter T of declval may be an incomplete type.
Anyway, here it would result in a non acceptable type (void&&
) and it works around it discarding the rvalue reference.
typename std::add_rvalue_reference<T>::type declval() noexcept; (since C++11) Converts any type T to a reference type, making it possible to use member functions in decltype expressions without the need to go through constructors.
add_rvalue_reference<T>
only results in T&&
if T
is a referenceable type. So when T
is void
, the result is just void
. This is also why you can add_rvalue_reference<int&&>
and not get an error attempting to construct a reference to a reference. (Same with lvalue reference.)
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