私は、プリミティブ/値型のプロパティへのアクセスを (合理的に) 可能な限り高速にし、できれば C++/CLR に保持することに重点を置いて、テンプレートをジェネリックに結合しようとしています。次の単純なテンプレートを検討してください。
template< typename type >
class value_wrapper {
public:
type value;
};
およびその対応物:
generic< typename T >
public ref class ValueWrapper {
...
public:
property T Value {
T get() {
if( T::typeid == System::Int32::typeid )
return ( T )( ( value_wrapper< int > * )ptr )->value;
...branches for some other types...
// if all else fails:
return ( T )( Object ^ )( ( value_wrapper< gcroot< Object ^ > > * )ptr )->value;
}
...
}
...
private:
void *ptr;
};
質問 1.ジェネリックの MSIL が値型の特殊化に変わると、コードはさらに最適化されますか? ValueWrapper<int>
たとえば、非 int 型の分岐や型比較自体が最適化されないように、ここで型をチェックすることは可能ですか?
ここで、すべてのメソッドでサポートされているすべての型をリストするのはやや面倒なので、このために別の関数を作成しました。
template< typename action, typename context_type >
__forceinline
static bool apply( System::Type ^type, void *value, System::Object ^*box, context_type context ) {
if( type == System::Int32::typeid )
return action().operator()< int >( ( int * )value, context ), true;
...branches for some other types...
// if all else fails:
return action().operator()< gcroot< System::Object ^ > >( box, context ), false;
}
struct get_value {
template< typename type, typename result_type >
void operator () ( result_type *result, void *ptr ) {
*result = ( ( value_wrapper< type > * )ptr )->value;
}
};
generic< typename T >
public ref class ValueWrapper {
...
property T Value {
T get() {
T result;
System::Object ^box;
return apply< get_value >( T::typeid, &result, &box, ptr ) ? result : ( T )box;
}
...
}
...
};
これは、元のコードよりも約 3 倍遅いことがわかりました。
質問 2.オプティマイザーが 2 番目の実装の速度を最初の実装に近づけるために、ここで何を変更できますか (理想的には、速度の差は 10% から 20% 以内)?
PS これは主に VC 2010 に関するものです。ただし、VC 2012 がこの点で何らかの違いがある場合は、それも知っておくとよいでしょう。