Note that there are some explanatory texts on larger screens.

plurals
  1. POGeneric wrappers for templates: optimization opportunities
    primarykey
    data
    text
    <p>I'm trying to marry templates to generics with the accent on making access to primitive/value-typed properties as fast as (reasonably) possible, preferrably keeping it in C++/CLR. Consider this simple template:</p> <pre><code>template&lt; typename type &gt; class value_wrapper { public: type value; }; </code></pre> <p>and its counterpart:</p> <pre><code>generic&lt; typename T &gt; public ref class ValueWrapper { ... public: property T Value { T get() { if( T::typeid == System::Int32::typeid ) return ( T )( ( value_wrapper&lt; int &gt; * )ptr )-&gt;value; ...branches for some other types... // if all else fails: return ( T )( Object ^ )( ( value_wrapper&lt; gcroot&lt; Object ^ &gt; &gt; * )ptr )-&gt;value; } ... } ... private: void *ptr; }; </code></pre> <p><strong>Question 1.</strong> When a generic's MSIL is turned into specializations for value types, is the code further optimized? Is it possible to check types here in such a way that, e.g., in <code>ValueWrapper&lt;int&gt;</code> branches for non-int types and type comparisons themselves will be optimized away?</p> <p>Now, listing all supported types in every single method is somewhat painful, so I have made a separate function for this:</p> <pre><code>template&lt; typename action, typename context_type &gt; __forceinline static bool apply( System::Type ^type, void *value, System::Object ^*box, context_type context ) { if( type == System::Int32::typeid ) return action().operator()&lt; int &gt;( ( int * )value, context ), true; ...branches for some other types... // if all else fails: return action().operator()&lt; gcroot&lt; System::Object ^ &gt; &gt;( box, context ), false; } struct get_value { template&lt; typename type, typename result_type &gt; void operator () ( result_type *result, void *ptr ) { *result = ( ( value_wrapper&lt; type &gt; * )ptr )-&gt;value; } }; generic&lt; typename T &gt; public ref class ValueWrapper { ... property T Value { T get() { T result; System::Object ^box; return apply&lt; get_value &gt;( T::typeid, &amp;result, &amp;box, ptr ) ? result : ( T )box; } ... } ... }; </code></pre> <p>Turns out this is about 3x slower than the original code.</p> <p><strong>Question 2.</strong> What can be changed here to allow the optimizer to make the second implementation closer in speed to the first one (ideally, with speed difference within 10%-20%)?</p> <p>P.S. This is mostly about VC 2010. But if VC 2012 is somehow different in this regard, that would be good to know, too.</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload