<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[Einsatzgebiet von Const-RValue-Referenzen]]></title><description><![CDATA[<p>Hallo,</p>
<p>Eine kurze Frage zu RValue-Referenzen in C++0x: Welchen Sinn haben RValue-Referenzen auf <code>const</code> -qualifizierte Typen, also <code>const T&amp;&amp;</code> ? Soweit ich das sehe, kann man <code>const</code> -RValues an sie binden, was bei <code>T&amp;&amp;</code> nicht geht.</p>
<p>Das wirft natürlich die Frage auf, wann man überhaupt <code>const</code> -qualifizierte RValues benötigt. Mir scheint, sie sind oft eine unnötige Einschränkung. Ich kann mir vorstellen, dass konstante RValues vor allem aus merkwürdigen Designs wie dem folgenden resultieren.</p>
<pre><code class="language-cpp">const Matrix operator+ (const Matrix&amp; lhs, const Matrix&amp; rhs);

// const-Rückgabe verhindert den immer wieder vorkommenden Fehler
// (a + b) = c; und macht daher alle Programme sicherer!
</code></pre>
<p>Denn bei RValues stört es ja prinzipiell niemanden, ob sie geändert werden (darin besteht schliesslich ein grosses Optimierungspotenzial durch Move-Semantik). Mit <code>const</code> kann man das temporäre Objekt hingegen nicht ändern und so kein Resource-Stealing betreiben.</p>
<p>Oder geht es mehr um lokale Sicherheit, also ähnlich wie hier?</p>
<pre><code class="language-cpp">void Function(const int i)
{
   // Ich kann i nicht aus Versehen ändern!
}
</code></pre>
<p>Dann verstehe ich aber nicht ganz, warum man nicht gleich <code>const T&amp;</code> statt <code>const T&amp;&amp;</code> nimmt. Möglicherweise, weil der Compiler beim Binden eines temporären Objekts an <code>const T&amp;</code> prinzipiell eine Kopie durchführen darf? Doch was für ein Compiler unterstützt RValue-Referenzen, optimiert aber so eine Kopie nicht weg?</p>
<p>Das Letzte, was ich mir vorstellen könnte, wäre Generizität. Also dass folgendes Konstrukt möglich ist, wenn <code>U</code>  <code>const</code> -qualifiziert ist.</p>
<pre><code class="language-cpp">typedef U&amp;&amp; rvalue_reference;
</code></pre>
<p>Dagegen ist eigentlich nichts einzuwenden. Aber gibt es einen Fall, in dem es vernünftig ist, explizit den Typen <code>const T&amp;&amp;</code> (für <code>T</code> irgendwas eingesetzt) zu benutzen?</p>
<p><em>Edit: Threadtitel</em></p>
]]></description><link>https://www.c-plusplus.net/forum/topic/278368/einsatzgebiet-von-const-rvalue-referenzen</link><generator>RSS for Node</generator><lastBuildDate>Tue, 25 Aug 2026 05:14:32 GMT</lastBuildDate><atom:link href="https://www.c-plusplus.net/forum/topic/278368.rss" rel="self" type="application/rss+xml"/><pubDate>Sun, 05 Dec 2010 16:22:11 GMT</pubDate><ttl>60</ttl><item><title><![CDATA[Reply to Einsatzgebiet von Const-RValue-Referenzen on Sun, 05 Dec 2010 21:58:18 GMT]]></title><description><![CDATA[<p>Hallo,</p>
<p>Eine kurze Frage zu RValue-Referenzen in C++0x: Welchen Sinn haben RValue-Referenzen auf <code>const</code> -qualifizierte Typen, also <code>const T&amp;&amp;</code> ? Soweit ich das sehe, kann man <code>const</code> -RValues an sie binden, was bei <code>T&amp;&amp;</code> nicht geht.</p>
<p>Das wirft natürlich die Frage auf, wann man überhaupt <code>const</code> -qualifizierte RValues benötigt. Mir scheint, sie sind oft eine unnötige Einschränkung. Ich kann mir vorstellen, dass konstante RValues vor allem aus merkwürdigen Designs wie dem folgenden resultieren.</p>
<pre><code class="language-cpp">const Matrix operator+ (const Matrix&amp; lhs, const Matrix&amp; rhs);

// const-Rückgabe verhindert den immer wieder vorkommenden Fehler
// (a + b) = c; und macht daher alle Programme sicherer!
</code></pre>
<p>Denn bei RValues stört es ja prinzipiell niemanden, ob sie geändert werden (darin besteht schliesslich ein grosses Optimierungspotenzial durch Move-Semantik). Mit <code>const</code> kann man das temporäre Objekt hingegen nicht ändern und so kein Resource-Stealing betreiben.</p>
<p>Oder geht es mehr um lokale Sicherheit, also ähnlich wie hier?</p>
<pre><code class="language-cpp">void Function(const int i)
{
   // Ich kann i nicht aus Versehen ändern!
}
</code></pre>
<p>Dann verstehe ich aber nicht ganz, warum man nicht gleich <code>const T&amp;</code> statt <code>const T&amp;&amp;</code> nimmt. Möglicherweise, weil der Compiler beim Binden eines temporären Objekts an <code>const T&amp;</code> prinzipiell eine Kopie durchführen darf? Doch was für ein Compiler unterstützt RValue-Referenzen, optimiert aber so eine Kopie nicht weg?</p>
<p>Das Letzte, was ich mir vorstellen könnte, wäre Generizität. Also dass folgendes Konstrukt möglich ist, wenn <code>U</code>  <code>const</code> -qualifiziert ist.</p>
<pre><code class="language-cpp">typedef U&amp;&amp; rvalue_reference;
</code></pre>
<p>Dagegen ist eigentlich nichts einzuwenden. Aber gibt es einen Fall, in dem es vernünftig ist, explizit den Typen <code>const T&amp;&amp;</code> (für <code>T</code> irgendwas eingesetzt) zu benutzen?</p>
<p><em>Edit: Threadtitel</em></p>
]]></description><link>https://www.c-plusplus.net/forum/post/1990122</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1990122</guid><dc:creator><![CDATA[Nexus]]></dc:creator><pubDate>Sun, 05 Dec 2010 21:58:18 GMT</pubDate></item><item><title><![CDATA[Reply to Einsatzgebiet von Const-RValue-Referenzen on Sun, 05 Dec 2010 18:00:38 GMT]]></title><description><![CDATA[<p>Nexus schrieb:</p>
<blockquote>
<p>Eine kurze Frage zu RValue-Referenzen in C++0x: Welchen Sinn haben RValue-Referenzen auf <code>const</code> -qualifizierte Typen, also <code>const T&amp;&amp;</code> ? Soweit ich das sehe, kann man <code>const</code> -RValues an sie binden, was bei <code>T&amp;&amp;</code> nicht geht.</p>
</blockquote>
<p>Wenn T deduziert wird, schon. Dann wird eben T = const Soundso. <img
      src="https://www.c-plusplus.net/forum/plugins/nodebb-plugin-emoji/emoji/emoji-one/1f642.png?v=ab1pehoraso"
      class="not-responsive emoji emoji-emoji-one emoji--slightly_smiling_face"
      title=":)"
      alt="🙂"
    /></p>
<p>Nexus schrieb:</p>
<blockquote>
<p>Das wirft natürlich die Frage auf, wann man überhaupt <code>const</code> -qualifizierte RValues benötigt.</p>
</blockquote>
<p>Warum soll man sie denn künstlich verbieten? Das erhöht doch nur die Zahl der Irregularitäten in C++.</p>
<p>Nexus schrieb:</p>
<blockquote>
<p>Mir scheint, sie sind oft eine unnötige Einschränkung. Ich kann mir vorstellen, dass konstante RValues vor allem aus merkwürdigen Designs wie dem folgenden resultieren.</p>
<pre><code class="language-cpp">const Matrix operator+ (const Matrix&amp; lhs, const Matrix&amp; rhs);

// const-Rückgabe verhindert den immer wieder vorkommenden Fehler
// (a + b) = c; und macht daher alle Programme sicherer!
</code></pre>
</blockquote>
<p>*seufz*<br />
Das soll ein immer wieder vorkommender Fehler sein? Das halte ich für ein Gerücht. Ich weiß, dass das einer von Scott Meyers' Tipps ist, aber wenn Du ihn heute fragen würdest, würde er sagen, dass das Zurückgeben von konstanten Objekten eine schlechte Idee sei, weil es &quot;Move-Semantics&quot; aushebelt. Das ist sogar belegt (findest Du in einer der C++ Newsgroups. Bin aber zu faul, das rauszusuchen).</p>
<p>Nexus schrieb:</p>
<blockquote>
<p>Denn bei RValues stört es ja prinzipiell niemanden, ob sie geändert werden (darin besteht schliesslich ein grosses Optimierungspotenzial durch Move-Semantik). Mit <code>const</code> kann man das temporäre Objekt hingegen nicht ändern und so kein Resource-Stealing betreiben.</p>
</blockquote>
<p>Genau.</p>
<p>Nexus schrieb:</p>
<blockquote>
<p>Oder geht es mehr um lokale Sicherheit, also ähnlich wie hier?</p>
<pre><code class="language-cpp">void Function(const int i)
{
   // Ich kann i nicht aus Versehen ändern!
}
</code></pre>
<p>Dann verstehe ich aber nicht ganz, warum man nicht gleich <code>const T&amp;</code> statt <code>const T&amp;&amp;</code> nimmt.</p>
</blockquote>
<p>Ich verstehe dieses Beispiel mit Deiner Bemerkung nicht. Ist da vielleicht ein Tippfehler dabei? Fehlt da ein &amp;&amp; im Code?</p>
<p>Nexus schrieb:</p>
<blockquote>
<p>Möglicherweise, weil der Compiler beim Binden eines temporären Objekts an <code>const T&amp;</code> prinzipiell eine Kopie durchführen darf? Doch was für ein Compiler unterstützt RValue-Referenzen, optimiert aber so eine Kopie nicht weg?</p>
</blockquote>
<p>Zusammenhang?</p>
<p>Nexus schrieb:</p>
<blockquote>
<p>Das Letzte, was ich mir vorstellen könnte, wäre Generizität. Also dass folgendes Konstrukt möglich ist, wenn <code>U</code>  <code>const</code> -qualifiziert ist.</p>
<pre><code class="language-cpp">typedef U&amp;&amp; rvalue_reference;
</code></pre>
<p>Dagegen ist eigentlich nichts einzuwenden. Aber gibt es einen Fall, in dem es vernünftig ist, explizit den Typen <code>const T&amp;&amp;</code> (für <code>T</code> irgendwas eingesetzt) zu benutzen?</p>
</blockquote>
<p>Ich verstehe Dich hier leider nicht.</p>
<p>Rvalue-Referenzen auf const können zB in folgenden Kontexten vorkommen:</p>
<p>reference_wrapper&lt;const string&gt; hat zwei Konstruktoren:<br />
...::reference_wrapper(const string &amp;);<br />
...::reference_wrapper(const string &amp;&amp;) = delete;<br />
(kann man also nicht mit Rvalue-Ausdrücken initialisieren, ob const oder nicht)</p>
<p>Bei Template-Argument-Deduktion:</p>
<pre><code class="language-cpp">template&lt;class T&gt;
void sink(T&amp;&amp;) {
  cout &lt;&lt; &quot;Argument war ein &quot;;
  if (is_lvalue_reference&lt;T&gt;::value) {
    cout &lt;&lt; &quot;Lvalue&quot;;
  } else {
    cout &lt;&lt; &quot;Rvalue&quot;;
  }
  cout &lt;&lt; &quot;-Ausdruck\n&quot;;
}

const string source();

void foo()
{
  sink(source()); // T = string const, T&amp;&amp; = string const&amp;&amp;
  const string s = source();
  std::ref(s);        // OK
  std::ref(source()); // Fehler, (c)ref/reference_wrapper mag keine Rvalues
}
</code></pre>
<p>Ich verstehe jetzt aber Dein Problem nicht ganz. const/non-const und &amp;-vs-&amp;&amp; sind größtenteils twei orthogonale Konzepte. Es gibt lediglich die Ausnahme, dass Du eine &quot;lvalue-Referenz auf const&quot; auch mit einem temporären Objekt initialisieren kannst. Das war's.</p>
<p>Gruß,<br />
kk</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1990149</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1990149</guid><dc:creator><![CDATA[krümelkacker]]></dc:creator><pubDate>Sun, 05 Dec 2010 18:00:38 GMT</pubDate></item><item><title><![CDATA[Reply to Einsatzgebiet von Const-RValue-Referenzen on Sun, 05 Dec 2010 21:57:34 GMT]]></title><description><![CDATA[<p>Vielen Dank für die Antwort. Ich habe übrigens die von dir empfohlene Artikel-Reihe auf C++Next angeschaut, danke nochmals dafür!</p>
<p>krümelkacker schrieb:</p>
<blockquote>
<p>*seufz*<br />
Das soll ein immer wieder vorkommender Fehler sein? Das halte ich für ein Gerücht.</p>
</blockquote>
<p>Hehe, das war ironisch gemeint. Ich bin völlig deiner Meinung. <img
      src="https://www.c-plusplus.net/forum/plugins/nodebb-plugin-emoji/emoji/emoji-one/1f642.png?v=ab1pehoraso"
      class="not-responsive emoji emoji-emoji-one emoji--slightly_smiling_face"
      title=":)"
      alt="🙂"
    /></p>
<p>krümelkacker schrieb:</p>
<blockquote>
<p>Ich verstehe dieses Beispiel mit Deiner Bemerkung nicht. Ist da vielleicht ein Tippfehler dabei? Fehlt da ein &amp;&amp; im Code?</p>
</blockquote>
<p>Nein, das sollte mehr eine Analogie sein. Mit &quot;lokaler Sicherheit&quot; meinte ich, dass Code innerhalb von <code>Function</code> nicht aus Versehen ein Objekt ändert, das nicht dazu vorgesehen ist. Ich bin kein Vertreter von Top-Level- <code>const</code> in Parametern. Bei RValue-Referenzen sind es zwar keine Top-Level-CVs mehr, aber der Gedanke (&quot;ich muss die Kopie nicht ändern, also mach ich sie konstant&quot;) könnte der gleiche bleiben. Ich habe mir halt ein paar Anwendungsfälle ausgedacht und überlegt, dass jemand Const-RValue-Referenzen zu diesem Zweck einsetzen könnte (was aber nicht allzu viel Sinn zu machen scheint).</p>
<p>krümelkacker schrieb:</p>
<blockquote>
<p>Zusammenhang?</p>
</blockquote>
<p>Wenn man das eben Beschriebene erreichen möchte, könnte man auch <code>const T&amp;</code> statt <code>const T&amp;&amp;</code> nehmen und hätte gleichzeitig auch LValues eingeschlossen. Als Nachteil von <code>const T&amp;</code> in diesem Zusammenhang ist mir nur die potenzielle unnötige Kopie in den Sinn gekommen.</p>
<p>krümelkacker schrieb:</p>
<blockquote>
<p>Ich verstehe jetzt aber Dein Problem nicht ganz. const/non-const und &amp;-vs-&amp;&amp; sind größtenteils twei orthogonale Konzepte.</p>
</blockquote>
<p>Ich beschäftige mich erst seit Kurzem mit C++0x-Konzepten und kenne daher noch kaum gebräuchliche Idiome oder Best Practices. Mir geht es nicht darum, RValue-Referenzen auf <code>const</code> ganz zu verbieten, schliesslich habe ich am Schluss auch Anwendungsfälle gesehen. Ich frage mich eher, ob es viele Kontexte gibt, in denen man sie direkt (nicht deduziert oder in Templates, sondern explizit) hinschreibt. Also wann man sowas programmiert:</p>
<pre><code class="language-cpp">class MyClass { ... };

void Function(const MyClass&amp;&amp; ref);
</code></pre>
<p>Bei &quot;normalen&quot; RValue-Referenzen ( <code>MyClass&amp;&amp; ref</code> ) kommt ja sowas ab und zu vor. Ich erkundige mich mehr nach dem Einsatzgebiet als nach dem Sinn von <code>const MyClass&amp;&amp;</code> (der Threadtitel ist etwas ungünstig, ich ändere ihn).</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1990247</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1990247</guid><dc:creator><![CDATA[Nexus]]></dc:creator><pubDate>Sun, 05 Dec 2010 21:57:34 GMT</pubDate></item><item><title><![CDATA[Reply to Einsatzgebiet von Const-RValue-Referenzen on Tue, 07 Dec 2010 20:04:24 GMT]]></title><description><![CDATA[<p>Hat jemand eine Idee für eine direkte Anwendung von <code>const T&amp;&amp;</code> ? Seid kreativ <img
      src="https://www.c-plusplus.net/forum/plugins/nodebb-plugin-emoji/emoji/emoji-one/1f642.png?v=ab1pehoraso"
      class="not-responsive emoji emoji-emoji-one emoji--slightly_smiling_face"
      title=":)"
      alt="🙂"
    /></p>
]]></description><link>https://www.c-plusplus.net/forum/post/1991233</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1991233</guid><dc:creator><![CDATA[Nexus]]></dc:creator><pubDate>Tue, 07 Dec 2010 20:04:24 GMT</pubDate></item><item><title><![CDATA[Reply to Einsatzgebiet von Const-RValue-Referenzen on Wed, 08 Dec 2010 00:31:03 GMT]]></title><description><![CDATA[<p>Nexus schrieb:</p>
<blockquote>
<p>Hat jemand eine Idee für eine direkte Anwendung von <code>const T&amp;&amp;</code> ? Seid kreativ <img
      src="https://www.c-plusplus.net/forum/plugins/nodebb-plugin-emoji/emoji/emoji-one/1f642.png?v=ab1pehoraso"
      class="not-responsive emoji emoji-emoji-one emoji--slightly_smiling_face"
      title=":)"
      alt="🙂"
    /></p>
</blockquote>
<p>siehe std::ref und std::cref zum Beispiel</p>
<pre><code class="language-cpp">template&lt;class T&gt;
reference_wrapper&lt;const T&gt; cref(T const&amp;);

template&lt;class T&gt;
void cref(T const&amp;&amp;) = delete;
</code></pre>
<p>--&gt; cref lässt sich nur mit Lvalues aufrufen -- aus Sicherheitsgründen.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1991293</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1991293</guid><dc:creator><![CDATA[krümelkacker]]></dc:creator><pubDate>Wed, 08 Dec 2010 00:31:03 GMT</pubDate></item><item><title><![CDATA[Reply to Einsatzgebiet von Const-RValue-Referenzen on Wed, 08 Dec 2010 18:42:24 GMT]]></title><description><![CDATA[<p>Ah, in deinem oberen Beispiel war das schon explizit und nicht deduziert, okay. Danke!</p>
<p>Vielleicht frag ich in 1-2 Jahren nochmals, wenn C++0x fertig ist und vielleicht auch von ein bisschen mehr Leuten verwendet wird. <img
      src="https://www.c-plusplus.net/forum/plugins/nodebb-plugin-emoji/emoji/emoji-one/1f609.png?v=ab1pehoraso"
      class="not-responsive emoji emoji-emoji-one emoji--winking_face"
      title=";)"
      alt="😉"
    /></p>
]]></description><link>https://www.c-plusplus.net/forum/post/1991630</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1991630</guid><dc:creator><![CDATA[Nexus]]></dc:creator><pubDate>Wed, 08 Dec 2010 18:42:24 GMT</pubDate></item></channel></rss>