2

我对 std::map 性能有疑问。在我的 C++ 项目中,我有一个GUIObjects 列表,其中还包括Windows。for我在循环中绘制所有内容,如下所示:

unsigned int guiObjectListSize = m_guiObjectList.size();
for(unsigned int i = 0; i < guiObjectListSize; i++)
{
    GUIObject* obj = m_guiObjectList[i];
    if(obj->getParentId() < 0)
    obj->draw();                                
}

在这种情况下,当我运行一个项目时,它可以顺利运行。我有 4 个窗口和一些其他组件,如按钮等。

但是我想单独处理绘制窗口,所以修改后,我的代码如下所示:

// Draw all objects except windows
unsigned int guiObjectListSize = m_guiObjectList.size();
for(unsigned int i = 0; i < guiObjectListSize; i++)
{
    GUIObject* obj = m_guiObjectList[i];
    if((obj->getParentId() < 0) && (dynamic_cast<Window*>(obj) == nullptr))
        obj->draw();        // GUIManager should only draw objects which don't have parents specified
                            // And those that aren't instances of Window class
                            // Rest objects will be drawn by their parents
                            // But only if that parent is able to draw children (i.e. Window or Layout)
}

// Now draw windows
for(int i = 1; i <= m_windowList.size(); i++)
{
    m_windowList[i]->draw(); // m_windowList is a map!
}

所以我创建了一个std::map<int, Window*>,因为我需要在地图中将 s 的 z-indexesWindow设置为keys。但问题是当我运行这段代码时,它真的很慢。尽管我只有 4 个窗口(地图大小为 4),但我可以看到 fps 速率非常低。我不能说一个确切的数字,因为我还没有实现这样的计数器。

谁能告诉我为什么这种方法这么慢?

4

2 回答 2

4

这就是虚函数的用途。你不仅消除了慢dynamic_cast,而且你得到了更灵活的类型检查。

// Draw all objects except windows
unsigned int guiObjectListSize = m_guiObjectList.size();
for(unsigned int i = 0; i < guiObjectListSize; i++)
{
    GUIObject* obj = m_guiObjectList[i];
    if(obj->getParentId() < 0)
        obj->drawFirstChance();
}

// Now draw windows
for(int i = 1; i <= m_windowList.size(); i++)
{
    m_windowList[i]->drawSecondChance();
}

WheredrawFirstChance对 windows 和其他浮动对象没有任何作用。

下一个优化机会是使窗口列表 avector并仅在其更改时执行 z 顺序排序(假设窗口的创建/销毁/重新排序的频率远低于绘制窗口的频率)。

于 2012-12-04T12:38:39.350 回答
2

这段代码的问题似乎与使用 std::map 无关。相反,瓶颈在于使用dynamic_cast,这是一个非常昂贵的操作,因为它需要遍历给定类的继承树。

对于您的 GUI 组件,这棵树很可能相当大,这肯定可以解释为什么在每次迭代中这样做会减慢整个方法的速度。

于 2012-12-04T12:27:53.607 回答