CVL共用行列・ベクトル演算ライブラリ作成大作戦


じぇえたかからのお願い

CVLMatrixクラスを使って、座標変換等を行う際にあると便利な関数群
(4月20日現在ではロールピッチヨー表現<->回転行列、
回転により1つのベクトルから別のベクトルに変換する回転行列を求めるのみ実装していますが)
を実装しようとしています。こんな関数がほしいというご意見をお待ちしております。


CVLで共用の行列・ベクトル演算ライブラリを使おうということで、
ためしに作ってみました。(ソースはこちら

更新情報


2002年

6月25日

4月20日

4月16日

4月8日(最近さぼってるなー)

1月27日

1月23日

1月17日

1月15日

1月8日

改良版作成中(CVLMatrix_beta)

2001年

12月16日

改良一応終了(旧バージョンをCVLMatrix->CVLMatrix1207へ)
サンプルプログラムをつけました
Quaternionは現在実装中

12月10日

改良版作成中(CVLMatrix_beta_version)

明日から大分なので今日はここらへんで勘弁してください
double型のやつはまだ書いてません
解説の書き直しはまた後日


解説

以下のような関数、及びクラスを作成しました。

場合に応じて使い分けてください。

関数群

<ベクトル演算>

1次元配列をベクトルとみなしてベクトル演算をする関数群には以下のようなものがある。

void CVLVect2fZero(float a[2]) // 2次元ベクトルを0で初期化
void CVLVect2fAdd(float a[2],const float b[2],const float c[2]) // 2次元ベクトルの足し算 a = b + c
void CVLVect2fSub(float a[2],const float b[2],const float c[2]) // 2次元ベクトルの引き算 a = b - c
void CVLVect2fScale(float a[2],float b,const float c[2]) // 2次元ベクトルのスカラー倍 a = b × c
float CVLVect2fDot(const float a[2],const float b[2]) // 2次元ベクトルの内積 a ・ b
float CVLVect2fLength(const float a[2]) // 2次元ベクトルの大きさ
void CVLVect2fCopy(float a[2],const float b[2]) // 2次元ベクトルの代入 a = b

また、3次元、4次元ベクトル用の関数群(CVLVect3f... CVLVect4f...という名の関数がそれに当たる)や
及び、浮動小数点にdouble型を用いた関数群(CVLVect?d... という名の関数がそれに当たる)
3次元ベクトルには特別に外積 a = b × c を求める関数
void CVLVect3fCross(float a[3],const float b[3],const float c[3])
void CVLVect3dCross(double a[3],const double b[3],const double c[3])がある


<行列演算>

1次元配列を行列とみなしたものと
(例えば2×2行列ならば

A= a[0] a[1]
a[2] a[3]

のようにとってあるとみなす)
2次元配列を行列とみなしたもの(a[行][列]のようにとる)に対して
行列演算をする関数群は以下のようなものがある

void CVLMat2fZero(float a[2][2]) // 2x2行列を0で初期化
void CVLMat2fZero2(float a[4])
void CVLMat2fInit(float a[2][2]) // 2x2行列に単位行列を代入
void CVLMat2fInit2(float a[4])
void CVLMat2fSet(float a[2][2],float b) // 2x2行列を単位行列倍 a = b I
void CVLMat2fSet2(float a[4],float b)
void CVLMat2fAdd(float a[2][2],float b[2][2],float c[2][2]) // 2×2行列の足し算 a = b + c
void CVLMat2fAdd2(float a[4],const float b[4],const float c[4])
void CVLMat2fSub(float a[2][2],float b[2][2],float c[2][2]) // 2×2行列の引き算 a = b - c
void CVLMat2fSub2(float a[4],const float b[4],const float c[4])
void CVLMat2fScale(float a[2][2],float b,float c[2][2]) // 2×2行列のスカラー倍 a = b × c
void CVLMat2fScale2(float a[4],float b,const float c[4])
void CVLMat2fMult(float a[2][2],float b[2][2],float c[2][2]) // 2×2行列の掛け算 a = b × c
void CVLMat2fMult2(float a[4],const float b[4],const float c[4])
float CVLMat2fTrace(float a[2][2]) // 2x2行列 a のトレース
float CVLMat2fTrace2(const float a[4])
float CVLMat2fDet(float a[2][2]) // 2x2行列 a の行列式
float CVLMat2fDet2(const float a[4])
void CVLMat2fCopy(float a[2][2],float b[2][2]) // 2×2行列の代入 a = b
void CVLMat2fCopy2(float a[4],const float b[4])
int CVLMat2fInv(float a[2][2],float \b[2][2]) // 2×2行列の逆行列 a = b-
int CVLMat2fInv2(float a[4],const float b[4])
void CVLMat2fTrans(float a[2][2],float b[2][2]) // 2×2行列の転置 a = bT
void CVLMat2fTrans2(float a[4],const float b[4])

3x3、4x4行列ようには特別にLU分解、およびそれを用いた交代代入がある

void CVLMat3fLUDec(float a[3][3],float b[3][3] // 行列 b のLU分解、結果はaへ
void CVLMat3fLUDec2(float a[9],const float[9]
void CVLMat3fBackSub(float x[3],float lu[3][3],const float b[3] // 交代代入してlu x = bをとく
void CVLMat3fBackSub2(float x[3],const float lu[9],const float b[3]

ベクトル演算と同様に3次元、4次元ベクトル用の関数群(CVLMat3f... CVLMat4f...という名の関数がそれに当たる)や
及び、浮動小数点にdouble型を用いた関数群(CVLMat?d... という名の関数がそれに当たる)がある。

<行列ベクトル複合演算>

行列とベクトルの掛け算をする関数がある

void CVLMat2MultVect2f(float a[2],float b[2][2],const float c[2]) // 2×2行列と2次元ベクトルの掛け算 a = b × c
void CVLMat2MultVect2f2(float a[2],const float b[4],const float c[2])

ベクトル演算と同様に3次元、4次元ベクトル用の関数群(CVLFMat3x3... CVLFMat4x4...という名の関数がそれに当たる)や
及び、浮動小数点にdouble型を用いた関数群(CVLDMat... という名の関数がそれに当たる)がある。

<クオータニオン演算>

1次元配列をクオータニオンとみなす([0]がスカラー部、[1..3]がベクトル部である)
クオータニオン演算群には以下のようなものがある

void CVLQuarfInit(float q[4]) // 単位クオータニオンで初期化 q=(1,0,0,0)
void CVLQuatfAA2Q(float q[4],const float axis[3],float angle) // 回転軸角度表現からクオータニオンへの変換
void CVLQuatfQ2AA(float axis[3],float *angle,const float q[4]) // クオータニオンから回転軸角度表現への変換
void CVLQuatfQ2M(float mat[3][3],const float q[4]) // クオータニオンから回転行列への変換
void CVLQuatfQ2M2(float mat[9],const float q[4])
void CVLQuatfM2Q(float q[4],float mat[3][3]) // 回転行列からクオータニオンへの変換
void CVLQuatfM2Q2(float q[4],const float mat[9])
void CVLQuatfCopy(float dest[4],const float src[4]) // 代入 dest = src
void CVLQuatfNeg(float dest[4],const float src[4]) // 符号の反転 dest=-src
void CVLQuatfInv(float dest[4],const float src[4]) // 逆クオータニオン dest=src~
void CVLQuatfAdd(float dest[4],const float src1[4],const float src2[4]) // クオータニオンの加算 dest=src1+src2
void CVLQuatfSub(float dest[4],const float src1[4],const float src2[4]) // クオータニオンの減算 dest=src1-src2
void CVLQuatfMult(float dest[4],const float src1[4],const float src2[4]) // クオータニオンの掛け算 dest=src1×src2
void CVLQuatfScale(float dest[4],float src1,const float src2[4]) // クオータニオンのスカラー倍 dest = src1×src2
void CVLQuatfMultVec(float dest[3],const float q[4],const float vec[3]) // クオータニオンによる座標変換 vec->dest
float CVLQuatfDot(const float src1[4],const float src2[4]) // クオータニオンの内積
void CVLQuatfNorm(float dest[4],const float src[4]) // 標準化(大きさ1)

double型のための演算 CVLQuatd...に関しても同様

<行列、ベクトル、クオータニオンクラス>

CVLVect[2..4][f,d] [2..4]次元のベクトルクラス
CVLMat[2..4][f,d] [2x2,3x3,4x4]行列のクラス

ベクトルクラスには以下のコンストラクタ、メンバ関数がある(CVLVect3fを例にあげる)

CVLVect3f() // 値は不定
CVLVect3f(float a,float b,float c) // (a,b,c)で初期化
CVLVect3f(const float a[3]) // (a[0],a[1],a[2])で初期化
CVLVect3f(const CVLVect3f& a) // aで初期化
CVLVect3f& operator=(const CVLVect3f& a) // 代入
CVLVect3f& operator=(const float a[3]) // 配列の値を代入
CVLVect3f& operator=(float a) // ベクトルの要素すべてをaにする
float& operator[](int a) // 要素へのアクセス
const float& operator[](int a) const
CVLVect3f operator+(const CVLVect3f& a) const // 加算
CVLVect3f operator-() const // 符号の反転
CVLVect3f operator-(const CVLVect3f& a) const // 減算
CVLVect3f operator*(float a) const // 乗算(スカラー倍)
CVLVect3f operator/(float a) const // 除算
CVLVect3f& operator+=(const CVLVect3f& a)
CVLVect3f& operator-=(const CVLVect3f& a)
CVLVect3f& operator*=(float s)
CVLVect3f& operator/=(float s)
float Dot(const CVLVect3f& a) const // 内積
float operator*(const CVLVect3f& a) const
CVLVect3f Cross(const CVLVect3f&) const // 外積(3次元ベクトルのみ)
CVLVect3f operator^(const CVLVect3f&) const
CVLVect3f operator^=(const CVLVect3f&)
float Length() const // 長さ

行列クラスには以下のコンストラクタ、メンバ関数がある(CVLMat3fを例にあげる)

CVLMat3f() // 値は不定
CVLMat3f(const float a[4]) // 配列の値で初期化
CVLMat3f(const float a[2][2])
CVLMat3f(const CVLMat3f& a) // 行列クラスの値で初期化
CVLMat3f& operator=(const CVLMat3f&) // 代入
CVLMat3f& operator=(const float a[4]) // 配列で表された行列の代入
CVLMat3f& operator=(const float a[2][2])
CVLMat3f& operator=(float a) // 単位行列のa倍を代入
CVLMat3f& operator=(const CVLQuatf&) // クオータニオンを回転行列に変換して代入(3×3行列のみ)
float* operator[](int) // 要素へのアクセス ex.) a[row][column] = 1
const float* operator[](int) const
CVLMat3f operator+(const CVLMat3f&) const // 加算
CVLMat3f operator-() const // 符号の反転
CVLMat3f operator-(const CVLMat3f&) const // 減算
CVLMat3f operator*(const CVLMat3f&) const // 乗算(行列同士)
CVLFVector2 operator*(const CVLFVector2&) const // 乗算(行列とベクトル)
CVLMat3f operator*(float) const // 乗算(スカラー倍)
CVLMat3f operator/(float) const // 徐算
CVLMat3f& operator+=(const CVLMat3f&)
CVLMat3f& operator-=(const CVLMat3f&)
CVLMat3f& operator*=(const CVLMat3f&)
CVLMat3f& operator*=(float)
CVLMat3f& operator/=(float)
CVLMat3f LUDec() const // LU分解(2x2にはない)
CVLMat3f Inv() const // 逆行列
CVLMat3f operator~() const
CVLMat3f Trans() const // 転置
float Trace() const // トレース
float Det() const // 行列式(determinant)

クオータニオンクラスには以下のコンストラクタ、関数がある

CVLQuatf() // 値は不定
CVLQuatf(const CVLQuatf &q) // クオータニオンクラスで初期化
CVLQuatf(const float q[4]) // 配列で初期化
CVLQuatf(float w,const CVLVect3f &v) // スカラー、ベクトルクラスで初期化
CVLQuatf(float w,const float v[3]) // スカラー、配列で初期化
CVLQuatf(const CVLVect3f &axis,float angle) // 回転軸角度表現から変換したクオータニオンで初期化
CVLQuatf(const float axis[3],float angle)
CVLQuatf(float w,float x,float y,float x) // スカラー、ベクトル(x,y,z)で初期化
void Init() // 単位クオータニオンに設定
float& operator[](int num) // ベクトル部へアクセス
const float& operator[](int num) const
float& W() // スカラー部へのアクセス
const float& W() const
CVLQuatf operator=(const CVLQuatf &q) // クオータニオンの代入
CVLQuatf operator=(const float q[4])
CVLQuatf operator=(const CVLMat3f &mat) // 回転行列をクオータニオンに変換して代入
int operator==(const CVLQuatf &q) // クオータニオンの比較
CVLQuatf operator+(const CVLQuatf &q) const // 加算
CVLQuatf operator-(const CVLQuatf &q) const // 減算
CVLQuatf operator*(const CVLQuatf &q) const // クオータニオン同士の掛け算
CVLVect3f operator*(const CVLVect3f &v) const // クオータニオンによる座標変換
CVLQuatf operator*(float s) const // クオータニオンのスカラー倍
CVLQuatf operator+=(const CVLQuatf &q)
CVLQuatf operator-=(const CVLQuatf &q)
CVLQuatf operator*=(const CVLQuatf &q)
CVLQuatf operator*=(float s)
float Dot(const CVLQuatf &q) const // クオータニオンの内積
CVLQuatf Norm() const // 標準化(大きさ1)
CVLQuatf Inv() const // 逆クオータニオン
CVLQuatf operator~() const
AA2Q(const CVLVect3d &axis,float angle) // 回転軸角度表現からクオータニオンへの変換
Q2AA(CVLVect3d &axis,float &angle) const // クオータニオンから回転軸角度表現への変換
M2Q(const CVLMat3f &mat) // 回転行列からクオータニオンへの変換
Q2M(CVLMat3f &mat) const // クオータニオンから回転行列への変換