模板类来关闭句柄和其他 WINAPI 的?

Template class to close HANDLES and other WINAPI's?

本文关键字:其他 WINAPI 关闭句柄      更新时间:2023-10-16

我刚接触C++,需要一些帮助。

到目前为止,我想制作一个处理HANDLE和其他WINAPI的模板class/struct,代码如下:

template <typename type_to_open, typename returntype, returntype (WINAPI * GlobalFn)(             
type_to_open )> class Handle_Wrap {
public:
type_to_open data;
Handle_Wrap (type_to_open in_data) { data = in_data; }
~Handle_Wrap() { returntype (WINAPI * GlobalFn)( type_to_open );}
};

Handle_Wrap <HANDLE, BOOL, ::FindClose> hFind ( FindFirstFileA (pattern.c_str(), &ffd) );

老实说,我认为它不起作用,编译器给了我一个警告:

warning C4101: 'GlobalFn' : unreferenced local variable

我从网上看到了这段代码,并对其进行了一些更改,我不知道这是否是正确的做法?

问题出在析构函数中。你重复声明GlobalFn,而不是调用它。它应该是:

~HandleWrap() { (*GlobalFn)( data ); }

此外,您想使此类可复制、可移动还是也不如果两者都没有,则应采取措施防止相关编译器生成的默认值;否则,您将需要提供相应的构造函数(并且可能赋值运算符)。如果是可复制的,你还需要一些计数器,在所有副本之间共享,因此只有最后一个析构函数释放句柄。对于可移动(可能是最佳解决方案,如果您可以确定拥有C++11),您将需要一个move构造函数,它可以确保moved-from对象的析构函数是no-op。

使用标准unique_ptr 怎么样

 std::unique_ptr<HANDLE, ::FindClose> hFind = FindFirstFileA(...);

(或者类似的东西)。

我怀疑您代码中的问题是,编译器不将GlobalFn视为函数调用,而是将其视为原型(Most Vexing Parse的另一个"胜利")-您根本不需要使用WINAPI,只需将其作为模板化的函数指针即可:

模板类Handle_Wrap{。。。~Handle_Wrap(){GlobalFn(数据);}};

您可能还想使用添加operator type_to_open() { return data; },这样您就可以使用FindNextFile(hFind, ...),而不必依赖于data是公共的。

相关文章: