title: Is the sub-object of a temporary object guaranteed to be moved on return?
body: <pre><code>#include &lt;string&gt;
  #include &lt;vector&gt;
  
  using namespace std;
  
  auto f()
  {
      vector&lt;string&gt; coll{ "hello" };
  
      //
      // Must I use move(coll[0]) ?
      //
      return coll[0]; 
  }
  
  int main()
  {
      auto s = f();
      DoSomething(s);
  }
  </code></pre>
  
  <p>I know: If I just <code>return coll;</code>, then <code>coll</code> is guaranteed to be moved on return.</p>
  
  <p>However, I am not sure: <strong>Whether <code>coll[0]</code> is also guaranteed to be moved on return?</strong></p>
  
  <p><strong>Update:</strong></p>
  
  <pre><code>#include &lt;iostream&gt;
  
  struct A
  {
      A() { std::cout &lt;&lt; "constructed\n"; }
      A(const A&amp;) { std::cout &lt;&lt; "copy-constructed\n"; }
      A(A&amp;&amp;) { std::cout &lt;&lt; "move-constructed\n"; }
      ~A() { std::cout &lt;&lt; "destructed\n"; }
  };
  
  struct B
  {
      A a;
  };
  
  A f()
  {
      B b;
      return b.a;
  }
  
  int main()
  {
      f();
  }
  </code></pre>
  
  <p>gcc 6.2 and clang 3.8 outputs the same:</p>
  
  <blockquote>
    <p>constructed</p>
    
    <p>copy-constructed</p>
    
    <p>destructed</p>
    
    <p>destructed</p>
  </blockquote>