迭代器从不执行yield break时,使用DoesNotReturnAttribute是否恰当?
问题解答
问题1:若自定义迭代器从不执行yield break语句,是否应为其标记DoesNotReturnAttribute特性?
绝对不应该。迭代器方法的核心是返回一个实现了IEnumerable<T>或IEnumerator<T>的状态机对象,哪怕没写显式的yield break,当枚举完所有yield return的元素后,状态机会自动进入终止状态,相当于隐式执行了yield break。而且调用迭代器方法本身就会直接返回状态机实例,不会卡住或永远不返回,完全不符合DoesNotReturnAttribute的适用场景——这个特性是给那些**永远无法正常返回(比如无限循环不退出、必然抛出异常)**的方法用的。
问题2:如下代码中使用DoesNotReturnAttribute是否恰当?
先看代码:
[DoesNotReturn] public static IEnumerable<int> X() { yield return 0; yield return 1; throw new Exception("Go away"); }
这个标记非常不恰当,原因很简单:迭代器的执行是延迟的。当你调用X()的时候,根本不会执行方法体里的任何代码,只会直接返回一个状态机对象,这属于正常返回。只有当你开始枚举这个IEnumerable<int>(比如用foreach遍历),才会逐步执行yield return,直到走到throw语句。但DoesNotReturnAttribute描述的是方法本身被调用后永远无法正常返回,而这个方法调用时明明能正常返回状态机,所以完全不符合特性的语义。
内容的提问来源于stack exchange,提问作者Hammerite
相关产品推荐
相关产品推荐

