0

我正在开发一个使用OpenSceneGraph的应用程序,我在if语句中遇到了一些奇怪的行为。我不确定它是否特定于API,因为它对我来说在任何级别上都毫无意义。使用if语句的奇怪行为

的代码:

if (!fileAddList_.empty()) 
{ 
    sg::FileStampThread::instance()->addFiles(fileAddList_); 
    fileAddList_.clear(); 
} 

其中:

  • fileAddList_:用于维持 文件名

  • FileStampThread自定义对象的静态矢量:一个OpenThreads对象的实例

  • 个addFiles():在线程的方法既节约了文件的列表 对象传递给它

上面的代码实现hotloading在我的应用程序。 FileStampThread实例不断运行,检查传递给它的文件名的时间戳。一旦图章发生变化,文件名将被保存到另一个列表中并传回以重新加载。

奇怪的是,即使没有要添加的文件(即使fileAddList_为空),场景图的更新遍历(在执行此代码时)也会显着减慢启用此代码段的速度)。结果是更新遍历时间增加了一个数量级。

但是,如果我注释掉对sg :: FileStampThread :: addFiles的调用,减速就会消失。然而,我已经将调用陷入调试模式,并且它永远不会被执行。

所以,我很困惑:当条件测试失败时,为什么条件内的一行代码会影响我的程序执行速度,并且从表面看,它从未被执行过?

作为一个方面说明,我怀疑它可能与将变量声明为静态有关,所以我尝试将它声明为全局(使用extern),而不是相同的效果。


的编辑处理一些下面的意见:

  • 线程是一个OpenThreads对象的实例。没有特定的MS 的东西,在这里。该实例是静态的。

  • addFiles()不是模板

  • 我测试与它的代码的循环。我交替注释掉了 这几行。我绝对积极的加入addFiles() 调用是罪魁祸首。

  • 调试与发布没有什么不同,将代码关闭到一个 单独的功能不改变,不幸的是,

  • OSG是高性能的,关于错误预测的评论可能是 。即将进行的研究...

代码为FileStampThread类:

void sg::FileStampThread::addFiles(sg::AssetFileList& files) 
{ 
    OpenThreads::ScopedLock<OpenThreads::Mutex> lock(contentMutex_); 

    for (sg::AssetFileList::iterator it = files.begin(); it != files.end(); ++it) 
    { 
     if (boost::filesystem::exists((*it).getPath())) 
      fileList_.push_back((*it)); 
    } 
}; 
+0

FileStampThread在COM部门?并且该类中使用了哪种线程安全性(使其成为一个安全的单例)? – 2012-03-21 11:49:51

+1

如果没有真正的问题和代码,很难看到。一个简单的答案*为什么会影响速度*可能是分支预测失误,但只有在紧密循环中执行时才会注意到它。如果这是一些高性能代码路径,请考虑为编译器添加提示。 – 2012-03-21 12:01:34

+0

好吧,理论上,如果addFiles是一个模板化的方法,那么你在某处调用它会导致它被实例化。你可以在addFiles里面做其他的模板实例,这些实例有全局的副作用。尽管这是一个很长的过程。 – enobayram 2012-03-21 12:25:24

回答

1

尝试移动代码:

sg::FileStampThread::instance()->addFiles(fileAddList_); 
fileAddList_.clear(); 

在一个单独的功能看,如果问题仍然存在。 难以摆脱正在发生的事情,在发布和调试版本上有相同的行为?

+0

+1用于描述有用的调试方法。 – 2012-03-21 13:19:32