为只能通过值传递的句柄编写包装类相对容易。我试图确定封装需要通过地址传递的句柄的最佳方法是什么。
例如,编写 SC_HANDLE 之类的包装器,通过值传递给 QueryServiceConfig()并不困难。可以实现 .GetHandle()之类的成员函数,也可以实现 operator()。
问题(至少对我而言)是像 RegOpenKeyEx()这样的API函数,它需要 HKEY 的地址。
我读过载重载算符&通常是一个坏主意。在允许API函数访问的同时,保持封装(或尽可能多的封装)以及特别是资源集合的推荐方法是什么?
答案 0 :(得分:2)
您始终可以添加另一个间接层,以避免operator&
和丑陋Attach
或Detach
的可怕重载,并从那里返回预先包装的实例。
如果您可以在VS2010或gcc中使用C ++ 0x,或者有其他方式访问std::unique_ptr<>
,那么您可以这样做(为简洁起见,省略了错误检查):
struct hkey_deleter
{
void operator()(HKEY hkey)
{
::RegCloseKey(hkey);
}
};
typedef std::unique_ptr<HKEY__, hkey_deleter> regkey;
regkey MyRegOpenKeyEx(HKEY hKey, LPCTSTR lpSubKey, DWORD ulOptions, REGSAM samDesired)
{
HKEY hOpenedKey = NULL;
::RegOpenKeyEx(hKey, lpSubKey, ulOptions, samDesired, &hOpenedKey);
return regkey(hOpenedKey);
}
void SomewhereElse()
{
...
regkey r = MyRegOpenKeyEx(HKEY_CLASSES_ROOT, nullptr, 0, KEY_READ);
...
}
hkey_deleter
将确保在退出作用域或调用regkey::reset()
时关闭注册表项。