[英]Cleaning up after variable declaration, initialization and unamanaged memory allocation
在定义变量,为变量分配空间,初始化变量然后正确清理所有内容时,我想请教您有关c#良好编程实践的建议。
我目前面临的问题是,我有一个使用非托管API函数的函数,因此也访问了非托管内存(使用了封送处理)。 我想使函数保持干净,并在退出之前妥善处理所有内容。 事实是,所有实际工作都在try-catch块内完成。 这意味着我不能在catch清洁家居或finally块。
我要做的是声明所有变量,为它们保留内存并在进入函数后立即对其进行初始化,然后在finally块中清理所有内容(关闭句柄,释放内存等)。
一切都很好,但我也想在try块中完成变量声明,初始化和内存分配(例如,初始化数组或在内存中分配空间或上帝知道位置时,也会出问题)。 唯一想到的是嵌套两个try-catch块。 这样可以吗?还是您会提出其他建议?
这是我到目前为止的内容:
//Declare variables, allocate memory, initialize variables.
........
try
{
//Do actual work - write to file and read from a file in my case
.........
}
catch (Exception exc)
{
//Exception handler for file write/read errors
}
finally
{
//Clean up (release handles, free memory,...)
}
这就是我的想法:
try
{
//Declare variables, allocate memory, initialize variables.
........
try
{
//Do actual work - write to file and read from a file in my case
.........
}
catch (Exception exc)
{
//Exception handler for file write/read errors
}
}
catch (Exception exc_1)
{
//Exception handler for variable declaration, initialization, memory allocation errors
}
finally
{
//Clean up (release handles, free memory,...)
}
预先感谢您的所有帮助!
干杯!
您可以实现IDisposable
接口以调用Dispose方法。
或作为最佳做法使用块using
using (var variable = .....)
{
...
}
使用块的特殊性是在处理结束时调用Dispose方法。
例如,如果您使用SqlConnection
var(var connection = new SqlConnection("...."))
{
....
}
仅此代码就足够了
链接: http : //msdn.microsoft.com/fr-fr/library/vstudio/system.idisposable.aspx
链接: http : //msdn.microsoft.com/fr-fr/library/yh598w02%28v=vs.80%29.aspx
该方法的问题是变量最终超出了范围(并捕获)
try
{
string testString;
}
catch (Exception ex)
{
}
finally
{
// testString is not in scope
}
您担心该声明可能会引发运行时错误吗?
基于注释,OP不知道初始化可以与声明分开。
List<string> testLString;
try
{
testLString = new List<string>();
}
catch (Exception ex)
{
}
finally
{
testLString = null;
}
我不同意您对声明可能引发运行时错误的担心。
它只做声明。
您可以根据需要嵌套任意数量的try...catch
结构。 这是使代码负责其自身清理的好方法。
也考虑使用仅try
并finally
处理总是需要清理的代码的结构,而不管它是否正常:
try {
// do something here
// declare some variable
try {
// allocate space for variable
// do something with that variable
} fincally {
// deallocate space for variable
}
// do something more here
} catch(Exception ex) {
// handle the exception here
}
您应该尝试使用尽可能具体的异常类,并且可以在同一结构中使用不同的类型来捕获不同的异常:
try {
// do some i/o
} catch (IOException ex) {
// here you know that it was actually the i/o that failed
} catch (Exception ex) {
// here is for catching anything else that might have failed
}
我建议您创建一个单独的类型,该类型包装与非托管API的所有通信,管理内存等。它实现IDisposable
接口,该接口的实现负责清理所有非托管资源。 如果您使用的是Windows,最简单的方法是在C ++ / CLI中实现此包装。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.