C ++ 11: STD: Move and STD: Forward source code analysis

Source: Internet
Author: User
Document directory
  • Prerequisites
  • STD: Move
  • STD: Forward

STD: Move and STD: forward are new standard library functions in C ++ 0x, which are used to implement Mobile semantics and perfect forwarding respectively.
Let's analyze the specific implementation of these two functions in gcc4.6.
Prerequisites

  1. Reference folding rules:
    X & + & => X &
    X & + & => X &
    X & + & => X &
    X & + & => X &&
  2. Function template parameter derivation rules (reference parameters on the right ):
    This rule applies when the template parameter of the function template is t and the function parameter is T & (reference to the right value.
    If the real parameter is left U &, the template parameter T should be derived as the reference type U &.
    (According to the reference folding rule, u & + & => U &, and T & <=> U &, so t <=> U &)
    If the real parameter is the right value U &, the template parameter T should be deduced as a non-reference type U.
    (According to the reference folding rule, U or U & + & => U &, while T &&, therefore, T <=> U or U &, which is mandatory here t <=> U)
  3. STD: remove_reference is a meta function in the C ++ 0x standard library. Its function is to remove references in the type.
    STD: remove_reference <u & >:: type <=> U
    STD: remove_reference <u & >:: type <=> U
    STD: remove_reference <u >:: type <=> U
  4. The following syntax converts expression T to the right value of the T type (specifically, it is a reference to the right value of the unknown)
    Static_cast <t &> (t)
  5. Note: <=> in this article, the meaning is "that is, equivalent to".
STD: Move

Function

STD: Move (t) is responsible for converting expression T to the right value. Using this conversion means that you no longer care about t content, it can be moved (stolen) to solve the mobile semantic problem.

Source code and test code

  template<typename _Tp>    inline typename std::remove_reference<_Tp>::type&&    move(_Tp&& __t)    { return static_cast<typename std::remove_reference<_Tp>::type&&>(__t); }
#include<iostream>using namespace std;struct X {};int main(){X a;X&& b = move(a);X&& c = move(X());}

Code Description

  1. Row 9th of the test code uses the left value a of the X type to test the move function. According to the right value of the standard X type, reference B can only bind the right value of the X type, so move () the return value must be the right value of the X type.
  2. Row 10th of the test code uses the right value x () of the X type to test the move function. C can only be bound to the right value of the X type according to the reference of the right value of the standard X type, therefore, the return value of move (x () must be the right value of the X type.
  3. First, we will analyze the situation where the move function is called with the left value parameter, such as move (.
  4. Simulate a single-step call to the source code line 3rd, _ TP & <=> X &, _ T <=>.
  5. According to the parameter deduction rules of the function template, _ TP & <=> X & available _ TP <=> X &.
  6. Typename STD: remove_reference <_ TP >:: type <=> X.
    Typename STD: remove_reference <_ TP>: Type & <=> X &&.
  7. One-step call again to go to the source code line 4th where the move function object is located.
  8. Static_cast <typename STD: remove_reference <_ TP >:: type &> (_ t) <=> static_cast <X &> ()
  9. According to the standard static_cast <X &> (A), the left value a is converted to an unnamed right value reference of the X type.
  10. Then we will analyze the situation of moving (x () using the right value parameter to call the move function.
  11. Simulate a single-step call to the source code line 3rd, _ TP &, _ T <=> X ().
  12. According to the parameter deduction rules of the function template, _ TP & amp; lt; & gt; X & amp; release _ TP <= & gt; X.
  13. Typename STD: remove_reference <_ TP >:: type <=> X.
    Typename STD: remove_reference <_ TP>: Type & <=> X &&.
  14. One-step call again to go to the source code line 4th where the move function object is located.
  15. Static_cast <typename STD: remove_reference <_ TP >:: type &> (_ t) <=> static_cast <X &> (x ())
  16. According to the standard static_cast <X &> (x (), the right value x () is converted to an unnamed right value reference of the X type.
  17. We can see from 9 and 16 that the specific implementation of the STD: Move function in the source code complies with the standard,
    Because no matter whether the left value A or the right value x () is used as a parameter to call the STD: Move function,
    This implementation will return an unnamed right value reference (one of the right values), which complies with the definition of this function in the standard.
STD: Forward

Function

STD: Forward <t> (u) has two parameters: T and U. When T is the reference type of the Left value, U is converted to the left value of the T type. Otherwise, U is converted to the right value of the T type. STD: Forward is defined to solve the perfect parameter forwarding problem in the function template that uses the right value to reference the parameter.

Source code and test code

  /// forward (as per N3143)  template<typename _Tp>    inline _Tp&&    forward(typename std::remove_reference<_Tp>::type& __t)     { return static_cast<_Tp&&>(__t); }  template<typename _Tp>    inline _Tp&&    forward(typename std::remove_reference<_Tp>::type&& __t)     {      static_assert(!std::is_lvalue_reference<_Tp>::value, "template argument"    " substituting _Tp is an lvalue reference type");      return static_cast<_Tp&&>(__t);    }
#include<iostream>using namespace std;struct X {};void inner(const X&) {cout << "inner(const X&)" << endl;}void inner(X&&) {cout << "inner(X&&)" << endl;}template<typename T>void outer(T&& t) {inner(forward<T>(t));}int main(){X a;outer(a);outer(X());}//inner(const X&)//inner(X&&)

Code Description

  1. Line 2 of the test code uses the left value of X type A to test the forward function. The program output indicates that outer (a) calls the inner (const X &) version, this proves that when the function template outer calls the forward function to forward the left value of parameter A to the inner function, the left Value Attribute of parameter A is successfully retained.
  2. Line 10 of the test code uses the right value of X () to test the forward function. The program output shows that outer (x () calls the inner (X &) version, this proves that when the function template outer calls the forward function to forward the right value x () of the parameter to the inner function, the right value attribute of the parameter x () is successfully retained.
  3. First, we will analyze the situation that outer (a) calls the forward function to forward the left value parameter.
  4. Simulate a one-step call to the test code line 8th, T & <=> X &, T <=>.
  5. According to the parameter deduction rules of the function template, T & <=> X & T <=> X & is available &.
  6. Forward <t> (t) <=> forward <X &> ().
  7. The second one-step call enters the source code line 4th or line 9th of the forward function entity.
  8. First try to match the forward function of source code 4th line, _ TP <=> X &.
  9. Typename STD: remove_reference <_ TP >:: type <=> X.
    Typename STD: remove_reference <_ TP>: Type & <=> X &.
  10. The parameter _ t is of the same type as the parameter A. Therefore, the function is matched successfully.
  11. Then try to match the forward function of source code line 9th, _ TP <=> X &.
  12. Typename STD: remove_reference <_ TP >:: type <=> X.
    Typename STD: remove_reference <_ TP>: Type & <=> X &&.
  13. The type of the parameter _ t is different from that of the real parameter A. Therefore, function matching fails.
  14. From 10 and 13, we can see 7. The forward function of source code 4th is actually called in one step.
  15. Static_cast <_ TP &> (_ t) <=> static_cast <X &> (a) <=>.
  16. Inner (Forward <t> (t) <=> Inner (static_cast <X &> (A) <=> Inner ().
  17. Outer (a) <=> Inner (Forward <t> (t) <=> Inner ()
    The next one-step call will go to the inner (const X &) version of line 5th of the test code. The left value parameter is successfully forwarded.
  18. Then, we will analyze the situation that outer (x () calls the forward function to forward the right value parameter.
  19. Simulate a one-step call to test the code line 8th, T & amp; lt; & amp; T & amp; lt; = & gt; X ().
  20. According to the parameter deduction rules of the function template, T & <=> X & T <=> X is available.
  21. Forward <t> (t) <=> forward <x> (x ()).
  22. The second one-step call enters the source code line 4th or line 9th of the forward function entity.
  23. First try to match the forward function of source code 4th line, _ TP <=> X.
  24. Typename STD: remove_reference <_ TP >:: type <=> X.
    Typename STD: remove_reference <_ TP>: Type & <=> X &.
  25. The parameter _ t is different from the real parameter x () type, so function matching fails.
  26. Then try to match the forward function of source code 9th, _ TP <=> X.
  27. Typename STD: remove_reference <_ TP >:: type <=> X.
    Typename STD: remove_reference <_ TP>: Type & <=> X &&.
  28. The parameter _ t is of the same type as the real parameter x (). Therefore, the function is matched successfully.
  29. From 25 and 28, we can see that 22. The forward function of source code 9th is actually called in one step.
  30. Static_cast <_ TP &> (_ t) <=> static_cast <X &> (x () <=> X ().
  31. Inner (Forward <t> (t) <=> Inner (static_cast <X &> (x () <=> Inner (x ()).
  32. Outer (x () <=> Inner (Forward <t> (t) <=> Inner (x ())
    The next one-step call will go to the inner (X &) version of line 6th of the test code. the right value parameter is successfully forwarded.
  33. From 17 and 32, we can see that the specific implementation of the STD: Forward function in the source code complies with the standard,
    Because no matter whether the left value A or the right value x () is used as a parameter to call the function template outer with the right value reference parameter,
    You only need to use the STD: Forward function to forward parameters in the outer function,
    The left and right values of parameters can be retained to achieve perfect forwarding of function template parameters.
Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.