LoginSignup
7
5

More than 5 years have passed since last update.

C++ 3次元配列の動的確保

Posted at

C++ 動的な3次元配列の利用

3次元配列を動的に確保する方法を記載する。
確保の方法について、混乱したので、自分なりに整理した。

確保する3次元配列のイメージ

3次元配列は以下のようなものをイメージする

Z:高さ
X:奥行
Y:横幅

3次元配列

3次元.PNG

メモリ確保

例)string型の以下のサイズの3次元配列を作成する
Z:高さ 5 
X:奥行 4
Y:横幅 6

実装は以下の手順で実施する

  1. トリプルポインタでポインタを宣言
  2. Z方向にメモリを必要数割り当て メモリ割り当てイメージ(緑色)
  3. Z方向に確保したメモリに対して、X方向にメモリを必要数を割り当て メモリ割り当てイメージ(青色)
  4. X方向に確保したメモリに対して、Y方向にメモリを必要数を割り当て メモリ割り当てイメージ(黄色)
    string ***cube = new string**[Z];   // 1,2
    for (int z = 0; z < Z; z++) {
        cube[z] = new string*[X]; // 3
        for (int x = 0; x < X; x++) {
            cube[z][x] = new string[Y]; // 4
        }
    }

メモリ割り当てイメージ

メモリ割り当て.PNG

メモリ開放

メモリ確保とは逆の手順で開放する

  1. X方向に確保したメモリに割り当てたY方向のメモリを解放
  2. Z方向に確保したメモリに割り当てたX方向のメモリを解放
  3. Z方向に確保したメモリを解放
    for(int z = 0; z < Z; z++) {
        for (int x = 0; x < X; x++) {
            delete[] cube[z][x]; // 1
        }
        delete[] cube[z]; // 2
    }
    delete[] cube; // 3

実装例

#include <iostream>
#include <string>
#include <sstream>      // std::ostringstream
using namespace std;

int main(void){

    // 3次元配列
    //     Z
    //     |
    //     |
    //     |___________Y
    //    /
    //   /
    //  X

    //
    // 3次元配列のサイズを入力
    //
    string str;

    cout << "?Y >";
    getline(cin, str);
    int Y = stoi(str);

    cout << "?X >";
    getline(cin, str);
    int X = stoi(str);

    cout << "?Z >";
    getline(cin, str);
    int Z = stoi(str);

    //
    // 3次元配列の動的確保
    // string型の3次元配列
    //
    string ***cube = new string**[Z];
    for (int z = 0; z < Z; z++) {
        cube[z] = new string*[X];
        for (int x = 0; x < X; x++) {
            cube[z][x] = new string[Y];
        }
    }

    //
    // 配列へのアクセス
    //

    // テスト用に適当なデータを設定する
    // (Z,X,Y) の形式で文字列データを設定
    for( int z = 0; z < Z; z++ ){
        for( int x = 0; x < X; x++ ){
            for( int y = 0; y < Y; y++ ){
                cube[z][x][y] = "(" + to_string(z) + "," + to_string(x) + "," + to_string(y) + ")";
            }
        }
    }

    // テスト用データの出力
    for( int z = 0; z < Z; z++ ){
        cout << "--- z(" << to_string(z) << ") ---" << endl;
        for( int x = 0; x < X; x++ ){
            for( int y = 0; y < Y; y++ ){
                cout << cube[z][x][y];
                if( y < (Y-1) ){
                    cout << ",";
                }
            }
            cout << endl;
        }
    }

    //
    // 3次元配列の開放
    //
    for(int z = 0; z < Z; z++) {
        for (int x = 0; x < X; x++) {
            delete[] cube[z][x];
        }
        delete[] cube[z];
    }
    delete[] cube;

    return 0;
}
7
5
6

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
5