2012-03-17 92 views
1

我已将范围缩小到派生类复制构造函数,但我不确定原因。 编辑: M,N和数据是私人的。我收到的错误是'无效的分配大小:4294967295字节' - 我明白是将-1传递给新的时产生的。我不确定为什么会发生这种情况,除非数据在班级交流时丢失。无效的分配大小(在派生类复制构造函数中)

BinaryMatrix::BinaryMatrix(const BinaryMatrix& copy) : Matrix(copy) 
{ 
    //cout << "Copy Constructor\n"; 

    M = copy.M; 
    N = copy.N; 

    data = new double[M*N]; //This line causes the allocation error 

    for (int i = 0; i < M; i++) 
    { 
      for (int j = 0; j < N; j++) 
      { 
        data[i*N+j] = copy.data[i*N+j]; 
      } 
    } 
} 

以上是我的派生复制构造函数,它会导致错误。我已经标记了分配线。

我只能假设M和N没有被正确读取。虽然我不确定为什么。我将包括派生和基础构造函数,以及基本副本。

感谢您的任何帮助。

MATRIX(BASE)构造

Matrix::Matrix(int M, int N, double* input_data) 
{ 
    this->M = M; 
    this->N = N; 

    //cout << "Matrix Constructor\n"; 
    data = new double[M*N]; 

    for (int i = 0; i < M; i++) 
    { 
      for (int j = 0; j < N; j++) 
      { 
        data[i*N+j] = input_data[i*N+j]; 
      } 
    } 

    delete [] input_data; 
} 

MATRIX(BASE)拷贝构造

Matrix::Matrix(const Matrix& copy) 
{ 
    //cout << "Copy Constructor\n"; 

    M = copy.M; 
    N = copy.N; 

    data = new double[M*N]; 

    for (int i = 0; i < M; i++) 
    { 
     for (int j = 0; j < N; j++) 
     { 
      data[i*N+j] = copy.data[i*N+j]; 
     } 
    } 
} 

BINARYMATRIX(派生)构造

BinaryMatrix::BinaryMatrix(int M, int N, double* input_data) : Matrix(M, N, input_data) 
{ 
    data = new double[M*N]; 

    for (int i = 0; i < M; i++) 
    { 
     for (int j = 0; j < N; j++) 
     { 
      this->data[i*N+j] = this->getRead(i, j); 
     } 
    } 

    double thr_val = this->Mean(); 

    for (int i = 0; i < M; i++) 
    { 
     for (int j = 0; j < N; j++) 
     { 
      if (this->data[i*N+j] > thr_val) 
       this->data[i*N+j] = 1; 

      if (this->data[i*N+j] < thr_val) 
       this->data[i*N+j] = 0; 
     } 
    } 
} 
+0

什么是错误? – Castilho 2012-03-17 15:19:49

+0

Doh - 对不起,我现在将其编辑为主要问题。 – LBHoward 2012-03-17 15:21:12

+0

这是运行时错误还是编译时错误? – je4d 2012-03-17 15:21:43

回答

0

如果MN是专用于MatrixBinaryMatrixMatrix派生,我不知道为什么你的代码编译(你不应该能够访问M,N中BinaryMatrix)。如果您的BinaryMatrix声明也包含成员MN(以及Matrix::NMatrix::M),那么这可能是问题的根源。

如果BinaryMatrix未声明MN,那么我认为我们仍然没有足够的数据来诊断您的问题。要猜测一下,也许M * N不适合用于M的类型。所以你有一个算术溢出。数组大小在size_t中指定,所以演员阵容将正常工作。

另外,您可能希望将数据的管理委托给其中一个类。也就是说,这样做无论是这样的:

BinaryMatrix::BinaryMatrix(const BinaryMatrix& copy) : Matrix(copy) 
{ 
    // M, N, data already set in Matrix::Matrix(const Matrix&) 
    // The data has also been copied, so there is nothing to do here. 
} 

或本:

#include <algorithm> 

BinaryMatrix::BinaryMatrix(const BinaryMatrix& copy) 
: Matrix(), M(0), N(0), 
    data(0) // null in case new throws an exception (avoid bad delete in dtor). 
{ 
    const size_t nelems(size_t(copy.M)*size_t(copy.N)); 
    data = new double[nelems]; 
    M = copy.M; 
    N = copy.N; 
    stl::copy(copy.data, copy.data+nelems, data); 
} 

我觉得一般是不使用int用于遍历动态数据结构是一个好主意,因为没有保证的实际大小的结构适合于int。但是,对于size_t(但任何现有对象都必须具有可在size_t中表示的大小,因此您可以使用size_t迭代任何连续对象),但该保证存在。

事实上,我不确定你想要从MatrixBinaryMatrix得到什么区别(目的或行为)。数据似乎具有相同的表示形式。如果它是行为的差异而不是你想要的表示,我认为使用组合(也就是单独的非继承表示类)而不是继承可能会更好。请参阅What is the Liskov Substitution Principle?了解如何有用地思考何时使用继承。但是,如果到目前为止您所看到的答案都不能真正帮助您解决问题,那么您应该花一些时间来减少您的示例:什么是可以证明您的问题的最小完整示例程序?发布。

+0

非常好,谢谢你的协助。这让我对继承和分配有了更深的理解。 :) – LBHoward 2012-03-17 15:48:23

+0

谢谢你的答案的进一步扩展。就我个人而言,在这种情况下我没有看到继承点。这是Uni任务之一,旨在以最抽象的方式教你一些东西。这些类的行为非常不同。二进制只允许1和0,但仍然使用双重来保存这些数据。非常不足。我还必须合并灰度,它将数据在0和255之间进行归一化。然而,您的答案提供了足够的洞察力来解决问题。没有必要重新定义Matrix(基础)已经做了什么。 – LBHoward 2012-03-17 16:02:13

+0

相反,我可以简单地使用派生的方法来执行标准化/转换为二进制。遵循重新运行的建议使用受保护类型可以实现这一点。 – LBHoward 2012-03-17 16:03:51

0

如果错误是M和N是私有的。那么您必须将保护级别更改为受保护或公开,或者提供一种访问方法。在私有基类中定义的可变参数对派生类是不可接受的。

class A 
{ 
    int x; 
} 

class B : public A 
{ 
    int DoSomething() 
    { 
     return x; //This is an error X is private to class A and as such inaccessible. 
    } 

} 
1

为什么你创建矩阵数据在BinaryMatrix拷贝构造一个新的副本?您从BinaryMatrix拷贝构造函数调用的Matrix的拷贝构造函数已经这样做了。

在你放弃Matrix拷贝构造函数已经取得的矩阵数据的副本BinaryMatrix拷贝构造函数(不delete荷兰国际集团的话),并创建一个新的。这是内存泄漏 - 如果你经常这样做,内存将会耗尽。

相关问题