2016-07-09 8 views
0

私はベクトルのマップの空のマップに値を挿入する機能を持っています。 (その特定の構造体は、オブジェクトをレンダリングするための複雑なソートのために必要です)。異なる値を返す同じオブジェクトへの2つのsize()呼び出し

しかし、私のデータは構造物のあるポイントで失われているように見えます。

(少し文脈で)私のメソッドのコードはここにある:

typedef unsigned int ComponentUID; 

//For the purposes of this example, assume the map is completely empty 
std::map<ComponentUID, std::map<float, std::vector<GameObjectPtr>>> renderOrderMap; 

void Render::addGameObjectToMap(GameObjectPtr objectPtr) { 

    //Expose the pointer for ease of use 
    GameObject *object = objectPtr.get(); 

    //Set up component local variables 
    RenderComponent *component = object->getRenderComponent(); 
    ComponentUID uid = component->getComponentUID(); 

    //Get object's render level (arbitrary float) 
    float renderLevel = object->getRenderLevel(); 

    //Find the location of the component UID in the render order map 
    std::map<ComponentUID, std::map<float, std::vector<GameObjectPtr>>>::iterator objectLocation = renderOrderMap.find(uid); 

    //If the object doesn't exist in the map 
    if (objectLocation == renderOrderMap.end()) { 

     //Add a new pair with the component UID and a fresh float/vector map and set the object location to the iterator pointing to it 
     objectLocation = renderOrderMap.insert(std::pair<ComponentUID, std::map<float, std::vector<GameObjectPtr>>>(uid, std::map<float, std::vector<GameObjectPtr>>())).first; 

     printf("Inserted pair"); 
    } 

    //Get the map at the value of the object location iterator 
    std::map<float, std::vector<GameObjectPtr>> objectMapping = objectLocation->second; 

    //Find the render level in the map 
    std::map<float, std::vector<GameObjectPtr>>::iterator vectorLocation = objectMapping.find(renderLevel); 

    //If the object doesn't exist in the map 
    if (vectorLocation == objectMapping.end()) { 

     //Add a new pair with the render level and a fresh GameObjectPtr vector and set the vector location to the pair's iterator 
     vectorLocation = objectMapping.insert(std::pair<float, std::vector<GameObjectPtr>>(renderLevel, std::vector<GameObjectPtr>())).first; 

     /* 
     * These two should equal the same value, because they should call the same method on the same object 
     */ 
     printf("Mapping size: %i", objectMapping.size()); //Outputs 1 
     printf("ExtraMapSize0: %i", renderOrderMap.find(uid)->second.size()); //Outputs 0 
    } 

    //Add the game object to the vector 
    std::vector<GameObjectPtr> objectVector = vectorLocation->second; 
    objectVector.push_back(objectPtr); 

} 

問題は2つのprintf文と底部付近にあります。理論的には同じオブジェクトを指すはずですが、最初の呼び出しで2番目の呼び出しと異なる値が返されます。

私のコードに問題はありますか?それともイテレータの仕組みについて根本的に誤解していますか?

+0

なぜ '.second'を' map :: insert'の戻り値でテストしませんでしたか? – PaulMcKenzie

答えて

1
std::map<float, std::vector<GameObjectPtr>> objectMapping = objectLocation->second; 

このコピーobjectMappingと呼ばれる新しいマップにobjectLocation->secondobjectMappingは新しいオブジェクトです。コピーはobjectLocation->secondから作成されています。

vectorLocation = objectMapping.insert(... 

これは、objectMappingオブジェクトに新しい値を挿入します。

/* 
    * These two should equal the same value, because they should call the same method on the same object 
    */ 
    printf("Mapping size: %i", objectMapping.size()); //Outputs 1 
    printf("ExtraMapSize0: %i", renderOrderMap.find(uid)->second.size()); //Outputs 0 

いいえ、それらは同じオブジェクトではありません。彼らは別のオブジェクトです。これは同じオブジェクトの同じメソッドを呼び出すのではなく、2つの異なる独立したオブジェクトの同じメソッドを呼び出すことです。そしてそれがあなたが同じ価値を得ていない理由です。

私はあなたが当初Java開発者であったと推測し、あなたは現在C++を学習しています。これはJavaでオブジェクトがどのように機能するかですが、C++のようには機能しません。 objectMappingという名前の新しいオブジェクトを宣言し、別のオブジェクトのコピーを他のオブジェクトのマップから作成しました。

本当にそれらを同じオブジェクトにしたい場合は、objectMappingを参照する必要があります。

std::map<float, std::vector<GameObjectPtr>> &objectMapping = objectLocation->second; 
+0

私は過去数年間JavaよりObjective-Cを多めにしてきました。私はちょうどこれが事実であるとすぐに分かりました、それはちょうど私が何とかそれを使用して&修正することを知らなかったのです – JamEngulfer

+2

単にそれを使用して&fixesを述べることは正確ではありません。より正確なステートメントは、「参照を使用して修正する」ことです。あなたが同じ問題を抱えていると思っている時はいつでも叩きつけているでしょう。生産的な結果を出すことはまずありません。 C++オブジェクトがどのように機能するかを理解することは重要であり、それにはポインタ、参照、スコープのトピックが含まれます。 *** *** C++オブジェクトモデル全体がどのように動作するかを理解することは、正しいコードを書くための鍵です。 –

0

しかし、あなたは同じことを印刷していません。

最初printfコールが第2の呼がrenderOrderMapからベクターのサイズを印刷std::map

あるobjectMappingのサイズを印刷します。

関連する問題