Skip to content

Instantly share code, notes, and snippets.

@sean-parent
Created September 18, 2013 17:37
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save sean-parent/6612672 to your computer and use it in GitHub Desktop.
Save sean-parent/6612672 to your computer and use it in GitHub Desktop.
Test move assignment by value.
#include <iostream>
using namespace std;
struct annotate {
annotate() { cout << "annotate ctor" << endl; }
annotate(const annotate&) { cout << "annotate copy-ctor" << endl; }
annotate(annotate&&) noexcept { cout << "annotate move-ctor" << endl; }
annotate& operator=(const annotate&) { cout << "annotate assign" << endl; return *this; }
annotate& operator=(annotate&&) noexcept { cout << "annotate move-assign" << endl; return *this; }
~annotate() { cout << "annotate dtor" << endl; }
};
struct annotate_value_assign {
annotate_value_assign() { cout << "annotate_value_assign ctor" << endl; }
annotate_value_assign(const annotate_value_assign&) { cout << "annotate_value_assign copy-ctor" << endl; }
annotate_value_assign(annotate_value_assign&&) noexcept { cout << "annotate_value_assign move-ctor" << endl; }
annotate_value_assign& operator=(annotate_value_assign x) noexcept { cout << "annotate_value_assign value-assign" << endl; return *this; }
~annotate_value_assign() { cout << "annotate_value_assign dtor" << endl; }
};
struct wrap1 {
annotate m_;
};
struct wrap2 {
annotate_value_assign m_;
};
int main() {
{
wrap1 x, y;
cout << "<move wrap1>" << endl;
x = move(y);
cout << "</move wrap1>" << endl;
}
{
wrap2 x, y;
cout << "<move wrap2>" << endl;
x = move(y);
cout << "</move wrap2>" << endl;
}
cout << boolalpha;
cout << "wrap1 nothrow move assignable trait:" << is_nothrow_move_assignable<wrap1>::value << endl;
cout << "wrap2 nothrow move assignable trait:" << is_nothrow_move_assignable<wrap2>::value << endl;
}
@sean-parent
Copy link
Author

clang -v
Apple LLVM version 4.2 (clang-425.0.28) (based on LLVM 3.2svn)
Target: x86_64-apple-darwin12.5.0
Thread model: posix

annotate ctor
annotate ctor
<move wrap1>
annotate move-assign
</move wrap1>
annotate dtor
annotate dtor
annotate_value_assign ctor
annotate_value_assign ctor
<move wrap2>
annotate_value_assign copy-ctor
annotate_value_assign value-assign
annotate_value_assign dtor
</move wrap2>
annotate_value_assign dtor
annotate_value_assign dtor
wrap1 nothrow move assignable trait:true
wrap2 nothrow move assignable trait:true

@l0calh05t
Copy link

g++ --version
g++ (rev0, Built by MinGW-builds project) 4.8.1

same behavior at least up to rev3

annotate ctor
annotate ctor
<move wrap1>
annotate move-assign
</move wrap1>
annotate dtor
annotate dtor
annotate_value_assign ctor
annotate_value_assign ctor
<move wrap2>
annotate_value_assign move-ctor
annotate_value_assign value-assign
annotate_value_assign dtor
</move wrap2>
annotate_value_assign dtor
annotate_value_assign dtor
wrap1 nothrow move assignable trait:true
wrap2 nothrow move assignable trait:true

@chenziliang
Copy link

I am using clang 3.4 built from source. The result of clang is the same as gcc 4.8.2.

ghost@ubuntu:~/work/test$ clang --version
clang version 3.4 (trunk 194323) (llvm/trunk 194323:194561)
Target: x86_64-unknown-linux-gnu
Thread model: posix

ghost@ubuntu:/work/test$ clang++ -std=c++11 -I /usr/gcc48/include/c++/4.8.2 -I /usr/gcc48/include -I /usr/gcc48/include/c++/4.8.2/x86_64-unknown-linux-gnu/ -I /usr/gcc48/include/c++/4.8.2/backward/ value.cxx
ghost@ubuntu:
/work/test$
ghost@ubuntu:~/work/test$ ./a.out
annotate ctor
annotate ctor

annotate move-assign
</move wrap1>
annotate dtor
annotate dtor
annotate_value_assign ctor
annotate_value_assign ctor

annotate_value_assign move-ctor <== it is moving instead of copying.
annotate_value_assign value-assign
annotate_value_assign dtor
</move wrap2>
annotate_value_assign dtor
annotate_value_assign dtor
wrap1 nothrow move assignable trait:true
wrap2 nothrow move assignable trait:true

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment