1

現在、タイルマップを作成しており、各タイルを保存および参照する方法を決定しようとしています。私の2つの現在のオプションは、次のいずれかです。

  1. 複合 x、y、z 計算をキーとして使用する std::vector。
  2. または、Vector3i をキーとして使用する std::map。

私の質問は次のとおりです。使いやすさやパフォーマンスに基づいて、どの方法を優先する必要がありますか。異なる方法間のメモリ/サイズ/ストレージも決定に入る可能性があると思います。これに基づいてエンジンを作成する前に、いくつかの意見が欲しいので、批判は大歓迎です。

複合ベクトルを使用した例を次に示します。

#include <vector>
#include <algorithm>
#include <iostream>

unsigned int mapWidth = 10, mapHeight = 10, mapDepth = 2;

struct Vector3i {
    Vector3i() {};
    Vector3i(unsigned int x, unsigned int y, unsigned int z) : x(x), y(y), z(z) {}
    unsigned int x, y, z;
};

struct Tile {
    Tile() {};
    std::vector<unsigned int> children;
    bool visible;
    Vector3i coord;
};

unsigned int getIndex(unsigned int x, unsigned int y, unsigned int z) {
    return (y*mapWidth) + x + (z * (mapWidth * mapHeight));
}

int main() {

    std::vector<Tile> tiles;
    tiles.resize(mapWidth * mapHeight * mapDepth);

    for( int x = 0; x < mapWidth; x++ ) {
        for( int y = 0; y < mapHeight; y++ ) {
            for( int z = 0; z < mapDepth; z++) {
                unsigned int idx = getIndex(x,y,z);
                tiles[idx].coord = Vector3i(x,y,z);
                tiles[idx].visible = true;
                tiles[idx].children.push_back(1);
            }
        }
    }

    std::for_each(tiles.begin(), tiles.end(), [&] (const Tile& tile) {
        std::cout << tile.coord.x << "," << tile.coord.y << "," << tile.coord.z << std::endl;
    });

    const Tile& myTile = tiles[getIndex(1,1,1)];
    std::cout << '\n' << myTile.coord.x << "," << myTile.coord.y << "," << myTile.coord.z << std::endl;

    return 0;
};

std::map メソッドを使用した例を次に示します。

#include <vector>
#include <map>
#include <iostream>
#include <algorithm>
#include <functional>

struct Vector3i {
    Vector3i() {};
    Vector3i(unsigned int x, unsigned int y, unsigned int z) : x(x), y(y), z(z) {}
    unsigned int x, y, z;
};

struct Tile {
    std::vector<unsigned int> children;
    bool visible;
    Vector3i coord;
};

class comparator {
    public:
        bool operator()(const Vector3i& lhs, const Vector3i& rhs) const {
            return lhs.x < rhs.x
                || ( lhs.x == rhs.x && ( lhs.y < rhs.y
                || ( lhs.y == rhs.y && lhs.z < rhs.z)));
        }
};

int main() {
    unsigned int mapWidth = 5, mapHeight = 5, mapDepth = 2;
    std::map<Vector3i, Tile, comparator> tiles;

    for( int x = 0; x < mapWidth; x++ ) {
        for( int y = 0; y < mapHeight; y++ ) {
            for( int z = 0; z < mapDepth; z++) {
                Vector3i key(z,y,x);

                Tile tile;
                tile.coord = Vector3i(x,y,z);
                tile.visible = true;
                tile.children.push_back(1);

                tiles.insert(std::make_pair<Vector3i, Tile>(key, tile));
            }
        }
    }

    for( std::map<Vector3i, Tile, comparator>::iterator iter = tiles.begin(); iter != tiles.end(); ++iter ) {
        std::cout << iter->second.coord.x << "," << iter->second.coord.y << "," << iter->second.coord.z << std::endl;
    }

    auto found = tiles.find(Vector3i(1,1,1));
    const Tile& myTile = found->second;
    std::cout << '\n' << myTile.coord.x << "," << myTile.coord.y << "," << myTile.coord.z << std::endl;

    return 0;
};

わかりました、たくさんありがとう!

4

1 に答える 1