C++ C+中的基本类设计+;,处理共同依赖类
我有两个类,一个是3D向量类(Vector3),它的成员是3个浮点数组(float[3]),另一个是3乘3矩阵类,它将这些向量中的3个存储在另一个数组中(Vector3[3])。我的vector类要求matrix类绕轴旋转,而matrix类要求所有东西都有向量。我使用了前向声明和指针来处理它,就像在这个问题中:,但必须有更好的方法来设计它,以完全避免这种情况。目前,我在我的矩阵头文件中声明了一个指向Vector3的指针,然后在我的实现文件中用new初始化它,但这感觉很笨拙。有没有关于如何解决这个问题的建议(没有双关语)? 编辑:我使用vector类来表示我打算绕任意轴旋转的3D点 我希望代码能够正常工作:C++ C+中的基本类设计+;,处理共同依赖类,c++,class,C++,Class,我有两个类,一个是3D向量类(Vector3),它的成员是3个浮点数组(float[3]),另一个是3乘3矩阵类,它将这些向量中的3个存储在另一个数组中(Vector3[3])。我的vector类要求matrix类绕轴旋转,而matrix类要求所有东西都有向量。我使用了前向声明和指针来处理它,就像在这个问题中:,但必须有更好的方法来设计它,以完全避免这种情况。目前,我在我的矩阵头文件中声明了一个指向Vector3的指针,然后在我的实现文件中用new初始化它,但这感觉很笨拙。有没有关于如何解决这个
//Vector3.h
#include "Matrix3.h"
class Matrix3;
class Vector3 {
float xyz[3];
};
//Vector3.cpp
Vector3 Vector3::rotatePoint(Vector3 o, Vector3 a, float theta) {
Vector3 point = (*this);
Vector3 x = Vector3(1,0,0);
Vector3 y = Vector3(0,1,0);
Vector3 z = Vector3(0,0,1);
// Create new coordinate system
Vector3 new_coord[4];
new_coord[0] = o;
new_coord[1] = a.normalize();
unsigned closer_to;
if (a*x < a*y) {
new_coord[2] = (a % x).normalize();
closer_to = 0; // x
}
else {
new_coord[2] = (a % y).normalize();
closer_to = 1; // y
}
new_coord[3] = (a % new_coord[2]).normalize();
// Transform point to new coord system
Matrix3 trans_matrix = Matrix3(new_coord[0], new_coord[1], new_coord[2]);
point = trans_matrix*(point - o);
// Rotate about a by theta degrees
Matrix3 r_m(closer_to, theta);
point = r_m*point;
//Transform back to original coord system
point = (trans_matrix.inverse()*point) + o;
return point;
}
//Matrix3.h
#include "Vector3.h"
class Vector3;
class Matrix3 {
Vector3 rows[3];
}
我采纳了@n.m.和@Chris Dodd的建议,从我的向量头中删除了Matrix3 include,并将其放入向量实现文件中,如下所示:
//Vector3.h
class Vector3 {
float xyz[3];
}
//Vector.cpp
#include "Vector3.h"
#include "Matrix3.h"
//Matrix3.h
#include "Vector3.h"
class Vector3;
class Matrix3 {
Vector3 rows[3];
}
//Matrix3.cpp
#include "Matrix3.h"
template<unsigned m, unsigned n, typename T = float>
class matrix {
T e[m * n];
public:
T* operator [](unsigned i) { return e + i; }
T * const operator [](unsigned i) const { return e + i; }
/* repeat for -, *, / -- same pattern */
matrix<m,n>& operator += (matrix<m,n> const& a) {
for (unsigned i = 0; i < m * n; ++i) e[i] += a.e[i];
return *this;
}
};
由于您处理的是向量和矩阵,因此可以使用维度模板(可能还有元素类型)定义单个矩阵类——然后向量类(取决于向量的类型)将是一个维度之一为1的矩阵。如果你这样做,你只会得到一个类,一组代码和所有你想要的功能。您可以避免任何类间依赖,因为您只有一个类 类本身看起来像这样:
//Vector3.h
class Vector3 {
float xyz[3];
}
//Vector.cpp
#include "Vector3.h"
#include "Matrix3.h"
//Matrix3.h
#include "Vector3.h"
class Vector3;
class Matrix3 {
Vector3 rows[3];
}
//Matrix3.cpp
#include "Matrix3.h"
template<unsigned m, unsigned n, typename T = float>
class matrix {
T e[m * n];
public:
T* operator [](unsigned i) { return e + i; }
T * const operator [](unsigned i) const { return e + i; }
/* repeat for -, *, / -- same pattern */
matrix<m,n>& operator += (matrix<m,n> const& a) {
for (unsigned i = 0; i < m * n; ++i) e[i] += a.e[i];
return *this;
}
};
模板
类矩阵{
te[m*n];
公众:
T*运算符[](无符号i){返回e+i;}
T*常量运算符[](无符号i)常量{返回e+i;}
/*对-、*、/--相同图案重复此操作*/
矩阵和运算符+=(矩阵常数和a){
对于(无符号i=0;i
然后,您应该定义任何函数,这些函数在类外不采用大小相等的矩阵(这就是为什么我们使用[]运算符)。请注意,*和/运算符作用于所有元素,不计算通常的矩阵乘法或矩阵除法。相反,您需要一个反转函数和一个乘法函数
template<unsigned m, unsigned n, unsigned k>
matrix<m,k> const multiply(matrix<m,n> const& a, matrix<n,k> const& b);
template<unsigned m>
matrix<m,m> const invert(matrix<m,m> const&);
template<unsigned m, unsigned n>
matrix<n,m> const transpose(matrix<m,n> const&);
模板
矩阵常数乘法(矩阵常数a、矩阵常数b);
样板
矩阵常数倒置(矩阵常数&);
样板
矩阵常数转置(矩阵常数&);
请注意,如果您有一种方法来反转一个通用的非方矩阵(我不知道其中的任何一种),那么上面的模板将只适用于一个方矩阵。作为练习,填写我留给您的函数的代码
要获得3矢量和3x3矩阵,您可以按如下方式键入它们:
typedef matrix<3,1,float> vector3f;
typedef matrix<3,3,float> matrix3x3f;
typedef矩阵向量3f;
类型定义矩阵矩阵x3f;
记住添加比较运算符以及您需要的任何其他内容
如果愿意,还可以添加矩阵标量、标量矩阵运算符和函数(以简化,例如,向矩阵中的所有元素添加标量)
如果希望更好地控制[]运算符中的元素,可以使用vectors作为基类,然后将矩阵定义为向量向量。这将给您带来相同的优势,但可能更适合您的思维方式(许多人认为向量和矩阵是不同的类型)。向量类不应该依赖于矩阵类。为什么矢量旋转依赖于矩阵?@Egg检查我的编辑。我使用矩阵将点转换为新的坐标系,使用旋转矩阵进行旋转,然后将点恢复到原始坐标系。我在想也许旋转不应该出现在vector类上,但我不知道放在哪里,这将是对它们的常见操作。
向量
不包含矩阵
,因此向量
声明只需要向前声明矩阵
(如果有)。一个矩阵
包含三个向量
,因此存在一个完整的依赖关系。将代码“按您的意愿”删除#包括向量3.h
中的行。现在一切都会好起来的。如果不是的话,你还有一些不应该有的奇怪的依赖性,你没有表现出你的问题是循环包含。向量3.h包括矩阵3.h,矩阵3.h包括向量3.h。这是行不通的。从Vector3.h中删除#包括“Matrix3.h”
,问题就会消失。