2010-11-23 9 views
0

は、次のような単純なコンテナ、他の方法を記述したり、それがあるとして、それは完全に賢明です:このコンテナ実装は完全に賢明ですか?

template <typename T, bool small_> 
struct TransType 
{ 
    typedef const T& param_type; 
}; 

template <typename T> 
struct TransType<T, true> 
{ 
    typedef const T param_type; 
}; 

template <class T> 
class Container:public TransType<T,sizeof(T)<=sizeof(void*)> { 
public: 
    param_type getVal(){ 
    return obj; 
    } 
    void setVal(param_type input){ 
    containment=input; 
    } 
private: 
    T containment; 
}; 
+1

テンプレート void UB(){TransType * x =新しいコンテナ; xを削除する。 //未定義の動作} ':P(基本クラスはパブリック仮想デストラクタまたは保護された非仮想デストラクタを必要とします) – GManNickG

+0

コンパイルされないという欠点があります;) – sth

+0

@GMan:継承を非公開にします。 *パブリック*ベースクラスは、パブリック仮想デストラクタまたは保護された非仮想デストラクタを必要とします。あるいは、標準ライブラリがどのようなものであり、基本クラスが何であるかによって多かれ少なかれ多様な削除のための基本クラスを使用することに関する文書化された禁止。私は誰かが 'std :: iterator'に何かをキャストしてそれを削除するために多くのプログラムが失敗したとは思いません。 –

答えて

1

Boost.CallTraitsを参照してください。すなわち、boost::call_traits<T>::param_type

タイプが小さいかどうかをクライアントが指定する必要はありません。これはメタ機能のジョブです。実際に何かを継承する必要はありません。

実際にあなたのコードは現在です。です。 param_typeは従属型ではないため、ルックアップは基本クラスを考慮せずに行われます。見つからないでしょう。明示的にそれを基底クラスで修飾するか、usingディレクティブを追加するか、それを再typedefする必要があります。今の状態は自動的に行われ、そして何の基底クラスの手間がありません

namespace detail 
{ 
    template <typename T, bool small_> 
    struct TransType 
    { 
     typedef const T& param_type; 
    }; 

    template <typename T> 
    struct TransType<T, true> 
    { 
     typedef const T param_type; 
    }; 
} 

template <typename T> 
struct TransType<T> 
{ 
    typedef detail::TransType<T, sizeof(T)<=sizeof(void*)> param_type; 
}; 

:によって

template <typename T> 
struct Container 
{ 
    //typedef typename boost::call_traits<T>::param_type param_type; 
    typedef typename TransType<T>::param_type param_type; 

    // ... 
}; 

あなただけで終わるしたいです。

1

私はメタ関数を継承しません。

0

明示的なデストラクタを必要とするというGManのコメントとは別に、追加された複雑さが大きなパフォーマンスを引き出すのでしょうか?標準ライブラリは、コピーがボトルネックにならないように、コンテナに適切なタイプを格納するのはユーザの責任であると考えていました。

+0

コピーが*予定*されているので、私はこの事前最適化は実際には無意味であると思います。私が持っている質問は、それは有害でしょうか? –

関連する問題