通过 Mex 开展一个关于 C++ 和 Matlab 合作的大型项目,我们目前正与我们的一个单身人士作斗争。
该类是在预处理期间通过宏生成的,因此看起来有点奇怪。
class AdditionalOperation {
private:
const std::string* val;
typedef std::map<std::string, const std::string*> StringMap;
static StringMap& getStringToPointerMap()
{
static StringMap map;
return map;
}
static boost::mutex& getMutex()
{
static boost::mutex mutex;
return mutex;
}
AdditionalOperation(const std::string* s)
:val(s)
{}
private:
static std::string* none_string()
{
static std::string s = "none";
static int count = 0;
boost::mutex::scoped_lock lock(getMutex());
if(count++ == 0) {
getStringToPointerMap().insert(std::make_pair(s,&s));
}
return &s;
}
public:
static AdditionalOperation none()
{
return AdditionalOperation(none_string());
}
private:
static std::string* norm_string()
{
static std::string s = "norm";
static int count = 0;
boost::mutex::scoped_lock lock(getMutex());
if(count++ == 0) {
getStringToPointerMap().insert(std::make_pair(s,&s));
}
return &s;
}
public:
static AdditionalOperation norm()
{
return AdditionalOperation(norm_string());
}
private:
static void prepare()
{
none();
norm();
}
public:
static AdditionalOperation fromString(std::string s)
{
static int count = 0;
if(count++ == 0)
prepare();
boost::mutex::scoped_lock lock(getMutex());
StringMap& map = getStringToPointerMap();
StringMap::iterator location = map.find(s);
if(location == map.end()) {
throw UnknownEnumValue(s);
}
return AdditionalOperation(location->second);
}
std::string toString() const
{
return *val;
}
bool operator==(const AdditionalOperation& other) const
{
return val == other.val;
}
bool operator!=(const AdditionalOperation& other) const
{
return !(*this == other);
}
};
所有这些代码都是从这一行生成的(通过如上所述的宏):
DECLARE_SENUM(AdditionalOperation, none, norm);
这是一个很好的界面,我们希望继续使用。
我们想使用这个类作为枚举的替代品,因为我们需要将它们从字符串转换为字符串。在这个类中,我们有 2 个“枚举”成员,即 norm 和 none。
现在我们添加了一些日志记录,并确定 none_string 和 norm_string 函数内的插入操作被调用了两次,即使我们的计数器应该阻止这种情况。
我们尝试过的一些事情:
- 我们正在使用动态库,但使用 -rdynamic 并没有帮助。
- 当我们打印静态变量的地址时,我们可以清楚地看到它们不同。
- 此类位于动态库中,该动态库又与 mex 文件链接。此 mex 文件正在由另一个 mex 文件通过 dlopen 动态加载。
我们在想,由于动态库,可能该类的多个实例被声明并处于活动状态。但是我们也使用了其他类型的没有任何问题迹象的单例。
我希望它足够清楚,可以随时提供额外的信息或澄清!
提前致谢!