c++ - 什么是 CInternetSession 的必要清理

标签 c++ mfc

CInternetSession::Close() 的 MSDN 文档只说

Call this member function when your application has finished using the CInternetSession object.

MSDN for CInternetSession::Close

对于 CHttpConnection CInternetSession::GetHttpConnection() 返回的对象, 和 CHttpFile CHttpConnection::OpenRequest() 返回的对象, 是否必须手动关闭和删除这些对象?

我找不到 CHttpConnection::Close() 的文档在 MSDN 上,和 CHttpFile继承其 Close()方法来自 CInternetFile ;其文档同样没有帮助:

Closes a CInternetFile and frees any of its resources.

(sorry, I can't have three links)

我的直觉假设是自 CInternetSession::GetHttpConnection()CHttpConnection::OpenRequest()返回指针,自 MSDN 以来 CHttpConnection

You never create a CHttpConnection object directly; rather, call CInternetSession::GetHttpConnection, which creates the CHttpConnection object and returns a pointer to it.

(sorry, I can't have three links)

那个CInternetSession在内部存储对 CHttpConnection 的引用它在 CInternetSession::Close() 时生成并清理了该对象叫做。这由 this MSDN article 支持,其中没有提及对连接对象的任何清理,并指出

Dispose of the CInternetSession object --> Automatically cleans up open file handles and connections.

小问题

这是必要的吗:

CInternetSession session(...);
CHttpConnection * connection = session.GetHttpConnection(...);
CHttpFile * file = connection->OpenRequest(...);

... Do stuff ...

file->Close();
delete file;

connection->Close();
delete connection;

session.Close();

或者这样做是否足够:

CInternetSession session(...);
CHttpConnection * connection = session.GetHttpConnection(...);
CHttpFile * file = connection->OpenRequest(...);

... Do stuff ...

session.Close();

元问题

如果---从库的文档中---不清楚清理资源的责任在哪里,检测资源泄漏的可能方法是什么?我知道 Valgrind 可用于内存泄漏,但文件句柄和其他可能被占用的资源呢?

最佳答案

简短的回答是您不必调用 Close(),它由 MFC 析构函数完成。理想情况下,析构函数应该进行所有必要的清理。

如您所述,MFC 类的文档很少。 WinINet 函数有更好的文档:

MSDN WinINet functions

例如,::InternetOpen 句柄必须用 InternetCloseHandle 关闭。我们可以查看 MFC 类的定义并进行比较:

C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\atlmfc\src\mfc\inet.cpp

CInternetSession(){
    ::InternetOpen //WinINet
    ...
}

CInternetSession::Close(){
    ::InternetCloseHandle //WinINet
    ...
}

CInternetSession::~CInternetSession(){
    Close();
}

所以我们不需要调用 internetSession.Close() 因为它是由析构函数自动完成的。调用它不会有什么坏处。我想如果 CInternetSession 是在堆上声明的,那么我们可能需要 Close() 因为它可能需要一些时间才能调用析构函数。

在另一个示例中,我们也不必调用 Close,但这并没有什么坏处。

CHttpFile * file = connection->OpenRequest(...);
file->Close();//I think this is okay but not necessary because we "delete file" in next line
delete file;//calls Close(); and other necessary cleanups

简短版:

CInternetSession session(...);
CHttpConnection *connection = session.GetHttpConnection(...);
CHttpFile *file = connection->OpenRequest(...);
//... Do stuff ...
delete file;//don't skip
delete connection;//don't skip
//session.Close();//you can skip, this gets called when we exist the function

顺便说一句,在 CInternetSession obj 上设置断点并单步执行,应该也会将您带到 MFC 文件 ..\VC\atlmfc\src\mfc\inet.cpp

关于c++ - 什么是 CInternetSession 的必要清理,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29703647/

相关文章:

c++ - 哪些 Netbeans 8.2 项目文件应该提交给 C++ 项目的版本控制?

c++ - 检测整数类型变量的空白输入?

GCC 的 C++ 库问题

multithreading - 如何在 MFC 中添加线程完成时的事件处理程序?

c++ - MFC 获取文件夹

c++ - std::future<neither::Either<int, std::string>> 段错误

C++:将类作为参数传递给其他类的方法

c++ - 文本字段如何响应 <Enter>

c++ - 使用 mfc 的动态菜单

c++ - MFC画圆