1

我有两个矩阵类,一个用于 CPU,一个用于 GPU,分别是MatrixCudaMatrix。声明和定义位于文件.h.cpp和. 在 中,我有.cuh.cumain

Matrix<int2_>      foo1(1,2);
// Definition of the elements of foo1...
CudaMatrix<int2_>  foo2(1,2);

cout << typeid(foo1).name() << "\n";
cout << typeid(foo2).name() << "\n";

// Equality
foo2=foo1;

现在,我在 a和 a之间没有operator=重载,但是我有以下重载CudaMatrixMatrixoperator=

const CudaMatrix& operator=(const CudaMatrix<LibraryNameSpace::int2_>&);

两者之间CudaMatrix。会发生以下情况:

  1. 这两个typeid返回正确的类foo1foo2;
  2. 上面的operator=重载是在运行时编译和调用的,用于foo2=foo1赋值。相反,我会预料到会出现编译错误;
  3. 分配的结果导致正确的结果foo2

我正在使用 Visual Studio 2010 并在发布模式下编译。

任何人都对为什么会发生这种明显不合逻辑的行为有一些提示?

谢谢。

4

1 回答 1

2

它们之所以起作用的关键是因为您同时拥有一个复制构造函数和一个显式复制赋值运算符。这两件事一起使看似未定义的案例正确运行。所以当你这样做时:

Matrix<int2_>      foo1(1,2);
CudaMatrix<int2_>  foo2(1,2);

foo2 = foo1;

发生的事情相当于:

Matrix<int2_>      foo1(1,2);
CudaMatrix<int2_>  foo2(1,2);

// foo2 = foo1;
{   
    CudaMatrix<int2_> x(foo1); // copy constructor
    foo2 = x; // Copy assignment
}

请注意,您应该在此处了解设备内存使用的影响(即两个设备内存分配和两组您在后台拥有的任何 API 调用)。

值得指出的是,这不是 CUDA 特有的,它是 C++98 对象模型的标准特性。如果您想了解更多关于它如何以及为什么起作用(以及为什么看似相似的反例不起作用),您可能会从修改三规则中受益。

于 2013-06-25T19:03:01.733 回答