C ++:向量大小错误且高于元素数

时间:2015-05-30 17:04:49

标签: c++ opengl vector

在我尝试加载.OBJ - 文件时,我将顶点数据加载到std::vectors以便稍后将它们发送到GPU。我填充三个向量,用于法线,顶点和纹理坐标。法向量的大小远远高于其他两个向量的大小,即使它填充了相同数量的元素。

代码:

SceneTree* generateSceneTree(OBJScene* scene){
    PostProcessing::triangulateFaces(scene);
    SceneNode* node = new SceneNode;

    vector<Vec<3>>& sceneNormals = scene->attributeData[Attribute::Normal];
    vector<Vec<3>>& sceneVertices = scene->attributeData[Attribute::Position];
    vector<Vec<3>>& sceneTexCoords = scene->attributeData[Attribute::TexCoord];

    map<string,MaterialInfo*> mtls;
    for(string s : scene->mtlLibs){
        auto temp = loadMTL(s);
        mtls.insert(temp.begin(),temp.end());
    }

    vector<Vec<3>> meshNormals;      <-- creating vectors here.
    vector<Vec<3>> meshVertices;
    vector<Vec<2>> meshTexCoords;
    for(auto g : scene->groups){
        meshNormals.clear();
            meshNormals.reserve(g.faces.size()*3);
        meshVertices.clear();
            meshVertices.reserve(g.faces.size()*3);
        meshTexCoords.clear();
            meshTexCoords.reserve(g.faces.size()*3);
        AABB bBox;
        cout << "num of faces: " << g.faces.size() << endl;
        for(auto f : g.faces){
            for(auto p : f.points){
                uint vIndex = p.indices[Attribute::Position];
                uint nIndex = p.indices[Attribute::Normal];
                uint tIndex = p.indices[Attribute::TexCoord];

                Vec<3> n = sceneNormals.at(nIndex);
                Vec<3> v = sceneVertices.at(vIndex);
                Vec<3> t = sceneTexCoords.at(tIndex);

                meshNormals.push_back(n);
                meshVertices.push_back(v);
                meshTexCoords.push_back(t.toVec<2>());

                bBox += meshVertices.back();
            }
        }
        cout << "meshNormals size: " << meshNormals.size() << endl;
        cout << "meshVertices size: " << meshVertices.size() << endl;
        cout << "meshTexCoords size: " << meshTexCoords.size() << endl;
        Mesh* m = new Mesh({
            {meshVertices,Attribute::Position},
            {meshNormals,Attribute::Normal},
            {meshTexCoords,Attribute::TexCoord}
        },GL_TRIANGLES);
        SceneLeaf* leaf = new SceneLeaf;
        leaf->nodeData = {Matrix4(),bBox};
        leaf->leafData = {m, mtls[g.mtlName]};
        node->addChild(leaf);
    }
    return node;
}

输出:

num of faces: 1087474
meshNormals size: 2958875950
meshVertices size: 3262422
meshTexCoords size: 3262422

这似乎非常不合逻辑。该程序在std::bad_array_new_length异常后崩溃,因为Mesh类无法创建一个大小为2958875950的数组以发送给GPU。

更新

如果我交换meshVerticesmeshNormals的声明,meshVertices的大小错误。所以第一个创建的向量会受到影响。

如果我使用std::list代替std::vector,一切正常。

如果我注释掉....reserve(g.faces.size()*3);行,则会抛出std::bad_alloc

2 个答案:

答案 0 :(得分:1)

简单的答案是你的指针在开头指向其他地方,或者:

  1. 你正在施展&#34;场景&#34;结构
  2. 在法线向量的场景结构中有垃圾或未设置指针。可能是你在放弃功能之前把垃圾放在那里。
  3. 你注意到2958875950是垃圾/负整数吗?

答案 1 :(得分:1)

我的猜测是你有一个“某处”的内存损坏错误,它会覆盖堆栈上的Group变量。交换meshNormalsmeshNormals声明的事实导致meshVertices与理论相匹配。

要缩小问题范围,您可以做一些事情:

  1. 注释掉内部meshVertices循环中的所有行,看看错误是否仍然存在。
  2. 假设没有,请逐个取消注释行,直到错误再次出现。
  3. 尝试制作一个复制问题的最小的,独立的测试代码示例(如果您在发布SO问题之前执行此操作,那将会非常有用)。