From c0b2c2f12dda44910eae1ae8298683134c764810 Mon Sep 17 00:00:00 2001 From: Vahagn Khachatryan Date: Mon, 5 Jan 2015 12:43:06 +0400 Subject: [PATCH] rvalue.cpp --- cpp/rvalue.cpp | 239 ++++++++++++++++++++++++++++++++++++++++ cpp/test_rvalue_ref.cpp | 68 ------------ 2 files changed, 239 insertions(+), 68 deletions(-) create mode 100644 cpp/rvalue.cpp delete mode 100644 cpp/test_rvalue_ref.cpp diff --git a/cpp/rvalue.cpp b/cpp/rvalue.cpp new file mode 100644 index 0000000..c229952 --- /dev/null +++ b/cpp/rvalue.cpp @@ -0,0 +1,239 @@ +/* +VIM: let g:lcppflags="-std=c++11 -O2 -pthread" +VIM: let g:wcppflags="/O2 /EHsc /DWIN32" +VIM: let g:argv="" +*/ + +#include +#include + +class copy_tracker +{ + int v; +public: + copy_tracker() + : v(0) + { + // std::cout << "copy_tracker::copy_tracker()" << std::endl; + } + + copy_tracker( const copy_tracker& c ) + : v( c.v ) + { + std::cout << "copy_tracker::copy_tracker( copy_tracker& c )" << std::endl; + } + + int use_object() const + { + return v; + } + + void non_const_method() + { + v++; + std::cout << "copy_tracker::non_const_method()" << std::endl; + } +}; + + +/* + * e + */ +#if 0 +// uncommenting this will cause compiler error due to ambiguity. +void e ( copy_tracker o ) +{ + std::cout << "e( ) by value called" << std::endl; + o.use_object(); +} +#endif + +void e ( copy_tracker& o ) +{ + std::cout << "e( & ) is called" << std::endl; + o.use_object(); +} + +void e ( const copy_tracker& o ) +{ + std::cout << "e( const & ) is called" << std::endl; + o.use_object(); +} + +void e ( copy_tracker&& o ) +{ + std::cout << "e( && ) is called" << std::endl; + o.use_object(); +} + +void e ( const copy_tracker&& o ) +{ + std::cout << "e( const && ) is called" << std::endl; + o.use_object(); +} + +/* + * f + */ +void f ( copy_tracker& o ) +{ + std::cout << "f( & ) is called" << std::endl; + o.use_object(); +} + +void f ( const copy_tracker& o ) +{ + std::cout << "f( const & ) is called" << std::endl; + o.use_object(); +} + +void f ( copy_tracker&& o ) +{ + std::cout << "f( && ) is called" << std::endl; + o.use_object(); +} + +/* + * g + */ +void g ( copy_tracker& o ) +{ + std::cout << "g( & ) is called" << std::endl; + o.use_object(); +} + +void g ( const copy_tracker& o ) +{ + std::cout << "g( const & ) is called" << std::endl; + o.use_object(); +} + +void g ( const copy_tracker&& o ) +{ + std::cout << "g( const && ) is called" << std::endl; + o.use_object(); +} + +/* + * h + */ +void h ( copy_tracker& o ) +{ + std::cout << "h( & ) is called" << std::endl; + o.use_object(); +} + +void h ( const copy_tracker& o ) +{ + std::cout << "h( const & ) is called" << std::endl; + o.use_object(); +} + +/* + */ +void s( const int & ) +{ + std::cout << "s( const int & ) is called" << std::endl; +} + +void s( int && ) +{ + std::cout << "s( int && ) is called" << std::endl; +} + +/* + */ + +void aaa( const std::string& s ) +{ + std::cout << s << std::endl; +} + +/* + * rvalue and const_rvalue + */ +copy_tracker rvalue() +{ + return copy_tracker(); +} + +const copy_tracker const_rvalue() +{ + return copy_tracker(); +} + +int main( void ) +{ + copy_tracker lvalue; + const copy_tracker const_lvalue; + // + // + // + std::cout << "The following modifies an rvalue." << std::endl; + // + rvalue().non_const_method(); + // + // + // + std::cout << "e is called for rvalue, const rvalue, lvalue, const lvalue." << std::endl; + // + e( rvalue() ); + e( const_rvalue() ); + e( lvalue ); + e( const_lvalue ); + // + // Const rvalue is handled by f( const & ) + // + std::cout << "f is called for rvalue, const rvalue, lvalue, const lvalue." << std::endl; + // + f( rvalue() ); + f( const_rvalue() );// f( const & ) + f( lvalue ); + f( const_lvalue ); + // + // Rvalue is handled by g( const && ) + // + std::cout << "g is called for rvalue, const rvalue, lvalue, const lvalue." << std::endl; + // + g( rvalue() );// g( const && ) + g( const_rvalue() ); + g( lvalue ); + g( const_lvalue ); + // + // Pre C++11 handling. h has only & and const & versions. + // + std::cout << "h is called for rvalue, const rvalue, lvalue, const lvalue." << std::endl; + // + h( rvalue() );// h(const &) + h( const_rvalue() );// h(const &) + h( lvalue ); + h( const_lvalue ); + // + // Try std::move + // + std::cout << "std::move." << std::endl; + // + e( std::move(rvalue()) );// e( && ) + e( std::move(const_rvalue()) );// e ( const && ) + e( std::move(lvalue) );// e( && ) + e( std::move(const_lvalue) );// e ( const && ) +#if 0 + // + // The following converts lvalue and const lvalue to rvalue and const + // rvalue. + // + std::cout << "std::forward lvalue and const lvalue." << std::endl; + // + e( std::forward(rvalue()) );// e( && ) + e( std::move(const_rvalue()) );// e ( const && ) + e( std::forward(lvalue) );// e( && ) + e( std::move(const_lvalue) );// e ( const && ) +#endif + + s( 5 );//s(int &&) + + aaa( "aaaa"); + + return 0; +} + diff --git a/cpp/test_rvalue_ref.cpp b/cpp/test_rvalue_ref.cpp deleted file mode 100644 index 8b02eb6..0000000 --- a/cpp/test_rvalue_ref.cpp +++ /dev/null @@ -1,68 +0,0 @@ - -#include -#include - -class copy_tracker -{ - int v; -public: - copy_tracker() - : v(0) - { - std::cout << "copy_tracker::copy_tracker()" << std::endl; - } - - copy_tracker( const copy_tracker& c ) - : v( c.v ) - { - std::cout << "copy_tracker::copy_tracker( copy_tracker& c )" << std::endl; - } - - void use_object() const - { - std::cout << v << std::endl; - } -}; - -copy_tracker create_rvalue() -{ - return copy_tracker(); -} - -const copy_tracker create_const_rvalue() -{ - return copy_tracker(); -} - -void f ( copy_tracker&& o ) -{ - o.use_object(); -} - -void f_const ( const copy_tracker&& o ) -{ - o.use_object(); -} - -void aaa( const std::string& s ) -{ - std::cout << s << std::endl; -} - -int main( void ) -{ - - f( create_rvalue() ); - - f_const( create_rvalue() ); - f_const( create_const_rvalue() ); - - copy_tracker lvalue; - f( std::move(lvalue) ); - f_const( std::move(lvalue) ); - - aaa( "aaaa"); - - return 0; -} -