C# 尝试捕获不安全代码中的异常
我正在编写一些图像处理代码,并使用C#进行低级像素处理。每隔一段时间,就会发生accessViolationExceptionC# 尝试捕获不安全代码中的异常,c#,image-processing,try-catch,unsafe,C#,Image Processing,Try Catch,Unsafe,我正在编写一些图像处理代码,并使用C#进行低级像素处理。每隔一段时间,就会发生accessViolationException 有几种方法可以解决这个典型的问题,有些人认为代码应该写得很健壮,这样就不会有访问冲突异常,就我所做的来说,应用程序运行得很好,但是我想添加一个try-catch,这样如果发生了什么事情,应用程序就不会以一种非常丑陋的方式失败 到目前为止,我已经输入了一些示例代码来测试它 unsafe { byte* imageIn = (byte*)img.ImageData.
有几种方法可以解决这个典型的问题,有些人认为代码应该写得很健壮,这样就不会有访问冲突异常,就我所做的来说,应用程序运行得很好,但是我想添加一个try-catch,这样如果发生了什么事情,应用程序就不会以一种非常丑陋的方式失败 到目前为止,我已经输入了一些示例代码来测试它
unsafe
{
byte* imageIn = (byte*)img.ImageData.ToPointer();
int inWidthStep = img.WidthStep;
int height = img.Height;
int width = img.Width;
imageIn[height * inWidthStep + width * 1000] = 100; // make it go wrong
}
当我对这个语句进行一次尝试时,我仍然得到一个例外。是否有方法捕获在不安全块中生成的异常
编辑:如下所述,除非通过将此属性添加到函数并添加“using System.Runtime.ExceptionServices”来显式启用对异常的检查,否则将不再处理此类异常
检查大小并返回
ArgumentOutOfRangeException
,如果参数使您在图像之外写入
AccessViolationException
是损坏状态异常(CSE),而不是结构化异常处理(SEH)异常。从.NET4开始,catch(异常e)
不会捕获CSE,除非您使用属性指定它。这是因为您首先应该编写避免CSE的代码。您可以在这里了解更多信息:“有些人认为代码应该写得很健壮,这样就不会有访问冲突异常”——我不清楚为什么您编写的代码不能以这样的方式避免异常。那么,为什么您不能查看异常并修复问题?修复这个可怕的问题!别把虫子埋了!如果你知道你写的是记忆,你就不能再写了。。你肯定会修正算法吗?你的算法显然有问题。。修复它。如果您遇到访问冲突,您可能已经损坏了数据。该计划应该在那时自杀。此时,您应该做的唯一一件事是记录日志,并可能将数据写入某个崩溃文件(不要简单地保存更改,它们可能已损坏!)以响应您编辑的答案,这不是一个好的解决方案。最终会产生一个部分修改的图像作为副作用。如果这应该是时间关键的,并且您多次调用该方法,那么异常处理将破坏性能。同意。也许更好的方法是写入日志文件(如果这样做,可能会永久损坏数据吗?),然后退出,而不是在没有任何详细信息的情况下退出?老实说,如果你只进行边界检查,你会很好,因为你能从数学上证明你不会在正确的边界之外写入,但是,如果您确实想在此处捕获异常,请确保您只捕获了AccessViolationException
,写出一条关于内存损坏的消息,然后Environment.Exit(1)代码>。通过边界检查,硬件内存损坏是唯一可能导致访问冲突的因素,发生这种情况的可能性极低。
[HandleProcessCorruptedStateExceptions]
public void makeItCrash(IplImage img)
{
try
{
unsafe
{
byte* imageIn = (byte*)img.ImageData.ToPointer();
int inWidthStep = img.WidthStep;
int height = img.Height;
int width = img.Width;
imageIn[height * inWidthStep + width * 1000] = 100; // to make it crash
}
}
catch(AccessViolationException e)
{
// log the problem and get out
}
}