Expression Template 其の一

早速、Expression Template(ET)を試してみることにした。
ずいぶん前に、買って置いたC++テンプレートテクニックを参考に実装してみる。
そのままでは詰まらないので、ベクトルの次元数を型情報としてテンプレート引数にとるようにしてみた。Traitsってやつか?
次元数を追い出したのはいいが、コンストラクタで初期化出来なくなってしまったので、Boostの真似をして代入用の演算子を定義しておいた。
が、、+=が使えなくなるので、シフト演算子あたりに変えようかな・・・。

以下、vector_types.h

#ifndef _vector_types_h_
#define _vector_types_h_

#include <assert.h>

namespace tml
{

typedef unsigned int    size_t;

// 型定義構造体
struct tagInt2 { typedef int Type; enum { Dim = 2 }; };
struct tagInt3 { typedef int Type; enum { Dim = 3 }; };
struct tagInt4 { typedef int Type; enum { Dim = 4 }; };
struct tagFloat2 { typedef float Type; enum { Dim = 2 }; };
struct tagFloat3 { typedef float Type; enum { Dim = 3 }; };
struct tagFloat4 { typedef float Type; enum { Dim = 4 }; };


// 本体
template<class _TypeTag>
struct Vector
{
    typedef typename _TypeTag::Type    Type;
    enum { Dim = _TypeTag::Dim };

    Type v[Dim];

    Vector()
    {
        for(int n = 0; n < Dim; n++) v[n] = 0.0f;
    }
    Vector(Type vv[])
    {
        for(int n = 0; n < Dim; n++) v[n] = vv[n];
    }

    // Expression Template用
    Type& operator[](size_t n) { return v[n]; }
    Type operator[](size_t n) const { return v[n]; }

    template<class _Expr>
    inline Vector<_TypeTag>& operator=(const _Expr &expr)
    {
        for(size_t i = 0; i < Dim; i++)
        {
            v[i] = expr[i];
        }

        return *this;
    }
};

// 代入簡略化
template<class _TypeTag, int N>
struct VectorAssigner
{
    Vector<_TypeTag> &v;

    VectorAssigner(Vector<_TypeTag> &vector) : v(vector) {}
    inline VectorAssigner<_TypeTag, N+1> operator,(typename _TypeTag::Type arg) // boostの真似
    {
        assert(N < _TypeTag::Dim); // 代入しすぎ

        v.v[N] = arg;
        return VectorAssigner<_TypeTag, N+1>(v);
    }
};

template<class _TypeTag>
inline VectorAssigner<_TypeTag, 1> operator+=(Vector<_TypeTag> &v, typename _TypeTag::Type arg)
{
    v.v[0] = arg;
    return VectorAssigner<_TypeTag, 1>(v);
}


} // namespace tml

#endif

Vector側に実装したのは代入演算子だけで、まだ、ETの部分は書いていない。
次はExpression Template本体をやる予定。。