Given this minimal example:
#include <iostream>
#include <stdexcept>
using std::cout;
using std::endl;
using std::runtime_error;
struct MyObj
{
MyObj() { cout << "constructed\n";}
MyObj(const MyObj& r) { cout << "copied\n"; }
MyObj(MyObj&& r) noexcept { throw runtime_error("I should terminate the program if uncaught"); }// = delete;
};
void Test(MyObj value)
{
cout << "called\n";
}
int main()
{
Test(MyObj());
return 0;
}
Here I (perceive to) implement all constructors that would be compiler implemented if left absent. I also confirmed I can get each one to execute given traditional invocations. The basis of my confusion lies in what main
does however.
Test
requires that whatever expression is passed to it, once evaluated, can be used to construct a discrete and independent value of MyObj
. My passing a previously non-existent default construction should yield an r-value reference &&
.
Trying to construct a value from an &&
is a perfect signature match to the implemented move constructor. In fact, if I declare that constructor as deleted (= delete;
), the compiler fails, saying a referenced function has been deleted, indicating my reasoning is at least marginally correct.
However, when I declare the function as written in the code example, an implementation destined to terminate the program if executed...nothing happens. I initially tried a cout
to mirror the other constructors, and nothing happened, so I added the runtime_error
to up the ante, or anti in this case. Nevertheless, the compiler warns a function declared noexcept
assuredly throws one, but compiles anyway and runs , printing:
constructed
called
I'm left with two questions.
Why does the compiler fail, claiming I am referencing a deleted function, if the executable will demonstrably never call it (in the
=delete;
case)?How is the parameter value in
Test
initialized from the r-value reference if neither by copy nor move?
NB: This is MSVC 14.11.25503 hosted by VS2017.
Edit: I just want to clarify, given the noexcept
specification, that throw
should terminate the program regardless.