无法在泛型方法中捕获构造函数

时间:2014-03-07 16:06:39

标签: c#

我无法在以下代码中捕获异常:

internal class Program {
    private class Wat {
        public Wat() {
            throw new Exception("how do i exception");
        }
    }

    private static T BreakIt<T>() where T : new() {
        return new T();
    }

    private static void Main(string[] args) {
        try {
            BreakIt<Wat>();
        } catch(Exception e) {
            Console.WriteLine("it broke: " + e.Message);
        }
    }
}

这也不起作用:

internal class Program {
    private class Wat {
        public Wat() {
            throw new Exception("how do i exception");
        }
    }

    private static T BreakIt<T>() where T : new() {
        try {
            return new T();
        } catch(Exception e) {
            Console.WriteLine("it broke: " + e.Message);
            return null;
        }
    }

    private static void Main(string[] args) {
        BreakIt<Wat>();
    }
}

但是,当构造函数没有抛出异常时它会起作用:

internal class Program {
    private class Wat {
        public void Break() {
            throw new Exception("how do i exception");
        }
    }

    private static T BreakIt<T>() where T : Wat, new() {
        T t = new T();
        t.Break();
        return t;
    }

    private static void Main(string[] args) {
        try {
            BreakIt<Wat>();
        } catch(Exception e) {
            Console.WriteLine("it broke: " + e.Message);
        }
    }
}

在调试和发布模式下都会发生这种情况。我的游戏是使用通用方法开始的,该方法完成所有设置,并且我正在尝试捕获崩溃记者的所有未处理的异常。

2 个答案:

答案 0 :(得分:2)

我认为发生这种情况是因为它实际上在后台创建了一个不同的异常,因此你的代码被框架代码而不是异常处理程序捕获。

在.NET中,你不能直接调用泛型类型参数的方法[1],所以方法

public static T New<T>() where T : new()
{
  return new T();
}

实际编译为

public static T New<T>() where T : new()
{
    if (default(T) != null)
    {
        return default(T);
    }
    return Activator.CreateInstance<T>();
}

(在发布模式下)。 Activate类显然使用了反射,它会处理原始异常并抛出TargetInvocationException

[1]您可以使用ilasm.exe编译IL代码,但是.NET和Mono将分别在加载方法或周围类型时抛出异常。

答案 1 :(得分:0)

如果只是在游戏框架内发生,可能this可能与它有关。

也许框架使用Tasks来分发工作。你可以在调试器停止后恢复执行吗?