2013-05-12 37 views
0

我正在编程A *代码,并尝试访问int **矩阵时出现了一个奇怪的“Segmentation Fault”问题。定义矩阵结构的内存分配

这里是矩阵的一个例子的代码。当我尝试t绘制第一个cout时,我获得了分段错误11.

#include <iostream> 

using namespace std; 

int main(int argc, char** argv) 
{ 
    int** matriz; 

    matriz = (int**) malloc(10 * sizeof(int)); 

    // Defino una matriz de 10x12 
    for (int i=0; i<10; i++) 
    { 
     matriz[i] = (int*) malloc(12 * sizeof(int)); 

     for (int j=0; j < 12; j++) 
     { 
      if(i == 11 && j == 5) 
       matriz[i][j] = 13; 
      else if(i == 10 && j == 7) 
       matriz[i][j] = 5; 
      else if(i == 3 && j == 11) 
       matriz[i][j] = 4; 
      else 
       matriz[i][j] = 0; 
     } 
    } 

    // Imprimo valores de prueba para comprobar que todos son accesible y que no encuentro un 'Segmentation Fault' 
    cout << "Valor en (11, 5) --> " << matriz[11][5] << endl; 
    cout << "Valor en (10, 7) --> " << matriz[10][7] << endl; 
    cout << "Valor normal 0 en (4, 4) --> " << matriz[4][4] << endl; 
    cout << "Valor en (3, 11) --> " << matriz[3][11] << endl; 

    return 0; 
} 

有人可以告诉我做错了什么。我不明白为什么我可以绘制坐标值(例如(4,4)和(3,11)),但是没有那些(11,5)或(10,7)靠近矩阵的偶数。

在此先感谢。

+0

这是C++代码。你张贴错误的部分。 – 2013-05-12 17:27:36

回答

2

如果使用C++(或更好,但C++11,例如与最近GCC -4.7或更好 - 编译器g++ -std=gnu++11 -Wall),你可以(至少或std::vector)使用std::array

,你应该至少代码

matriz = (int**) malloc(10 * sizeof(int*)); 
    if (!matriz) { perror("malloc matriz"); exit(EXIT_FAILURE); }; 

(我的Linux /于Debian/x86-64的机器上,sizeof(int)是4,但sizeof(int*) 8)

因为matriz每个元素,例如matriz[3]是一个指针。

我宁愿建议在C++ 11使用std::array和编码所有的

auto matriz = new std::array<std::array<int,12>,10>(); 

#include <array>

+0

我通常使用C++ standar结构vector或deque,但现在我使用malloc和指针来记住这些概念。 – 2013-05-12 17:31:52

+0

我应用你建议我的修改,但问题仍然存在。我使用OS X和g ++来编译代码。 – 2013-05-12 17:34:47

+0

然后,学习使用g ++ -Wall -g' – 2013-05-12 17:38:32

3

首先,你可以阅读Why pointer to pointer and vector of vector is bad for simple matrices。您需要输入密码“p2pbad”(不含“”)。

此行

cout << "Valor en (11, 5) --> " << matriz[11][5] << endl; 

将尝试访问,因为你的矩阵只有10行,但你想从第11行获得的数据中不存在的元素 - >段故障。 出于同样的原因,条件

if(i == 11 && j == 5) 

没有意义。我将永远不会是11,也不会因为i<10而在下一个条件中成立i == 10

为通用矩阵处理编写真正好的代码是一项艰巨的任务,但您可以用一些努力编写简单/基本的模板化矩阵类。使用std ::分配器

一个基本的例子是像

template <typename _T> 
class basic_matrix 
{ 
public: 
    typedef basic_matrix<_T>    this_type; 
    typedef ::std::allocator<_T>   alloc; 
    typedef typename alloc::value_type  value; 
    typedef typename alloc::pointer   ptr; 
    typedef typename alloc::const_pointer const_ptr; 
    typedef typename alloc::reference  ref; 
    typedef typename alloc::const_reference const_ref; 
    typedef typename alloc::size_type  size; 
    typedef typename alloc::difference_type diff; 
    typedef _T&&       r_ref; 

    basic_matrix (void) 
    : _data(nullptr), _x(0U), _y(0U) 
    { 
    } 

    basic_matrix (size const & x, size const & y) 
    : _data(nullptr), _x(0U), _y(0U) 
    { 
    resize(x,y); 
    } 

    ~basic_matrix (void) 
    { 
    if (!empty()) clear(); 
    } 

    void resize (size const &x, size const &y) 
    { 
    if (x == 0 && y == 0) 
    { 
     clear(); 
    } 
    else 
    { 
     ptr new_location = _Allocate(x*y); 
     if (!empty()) 
     { // old data existent -> copy it 
     try 
     { 
      size const N = min(x, _x), M = min(y, _y); 
      for (size i=0; i<N; ++i) 
      { 
      for (size j=0; j<M; ++j) 
      { 
       *(new_location + i*y + j) = *(_data + i*_y + j); 
      } 
      } 
     } 
     catch (...) 
     { 
      _Deallocate(new_location, x*y); 
      clear(); 
      throw; 
     } 
     } 
     _data = new_location; 
     _x = x; 
     _y = y; 
    } 
    } 

    ref operator() (size const &x, size const &y) 
    { 
    if (x >= _x || y >= _y) throw std::exception("OUT OF RANGE"); 
    return *(_data + x*_y + y); 
    } 

    const_ref operator() (size const &x, size const &y) const 
    { 
    if (x >= _x || y >= _y) throw std::exception("OUT OF RANGE"); 
    return *(_data + x*_y + y); 
    } 

    bool empty (void) const 
    { 
    return (_data == nullptr); 
    } 

    void clear (void) 
    { 
    _Deallocate(_data, _x*_y); 
    _data = nullptr; 
    _x = 0U; 
    _y = 0U; 
    } 

protected: 

    ptr _data; 
    size _x, _y; 
    alloc _allocator; 

    ptr _Allocate (size const &num) 
    { 
    ptr new_location; 
    try 
    { 
     new_location = _allocator.allocate(num); 
    } 
    catch (...) 
    { 
     clear(); 
     throw; 
    } 
    return new_location; 
    } 

    void _Deallocate (ptr location, size const &num) 
    { 
    _allocator.deallocate(location, num); 
    } 

}; 

你将被要求增加拷贝构造函数和赋值运算符和一些其他的东西......无论你想你的矩阵接口表现得像......

这工作使用这样的代码:

int main (void) 
{ 

    basic_matrix<int> matriz(10, 12); 

    // Defino una matriz de 10x12 
    for (int i=0; i<10; i++) 
    { 
     for (int j=0; j < 12; j++) 
     { 
      if(i == 9 && j == 7) 
       matriz(i,j) = 5; 
      else if(i == 3 && j == 11) 
       matriz(i,j) = 4; 
      else 
       matriz(i,j) = 0; 
     } 
    } 
    cout << "Valor en (10, 7) --> " << matriz(9,7) << endl; 
    cout << "Valor normal 0 en (4, 4) --> " << matriz(4,4) << endl; 
    cout << "Valor en (3, 11) --> " << matriz(3,11) << endl; 
    return 0; 
} 

它打印:

Valor en (10, 7) --> 5 
Valor normal 0 en (4, 4) --> 0 
Valor en (3, 11) --> 4 
+0

感谢您的解释。它帮助我很多。 – 2013-05-12 21:18:59