什么是语句的不可到达端点(不可达端点)?

时间:2013-03-01 22:41:24

标签: c#

受到这个问题答案的启发 Is empty case of switch in C# combined with the next non-empty one?

此术语的唯一出现在C#语言规范的第6.5节中

  
      
  • 如果D具有非void返回类型且F的主体是语句块,则F的每个参数都被赋予D中相应参数的类型1}},F的主体是一个有效的语句块(wrt§8.2),带有 不可到达的端点 ,其中每个return语句指定一个可隐式转换为返回类型D的表达式。
  •   

在规范中我们可以看到

  
      
  • 8.1终点和可达性

         每个语句都有一个端点。直观地说,语句的终点是紧跟语句的位置。复合语句(包含嵌入语句的语句)的执行规则指定控件到达嵌入语句的结束点时所采取的操作。例如,当控件到达块中语句的结束点时,控制权将转移到块中的下一个语句。
      ...
  •   

我们可能对此有所了解。但是,我用Google搜索并发现没有直接解释 不可访问的端点 。因为Stack Overflow是一个Q& A站点,我认为如果有一个更简单和更直观的解释,可以轻松搜索和理解这个术语将有助于程序员,特别是那些不是母语为英语的人。

2 个答案:

答案 0 :(得分:2)

Ben的回答很好地理解了它。为了更精确,终点:

  • 断裂
  • 继续
  • 转到
  • 返回

语句无法访问。这些语句中的每一个都在“结束之前”将控制转移到其他地方,因此语句的“终点”永远不会被命中。将其与以下语句进行比较:

  • Console.WriteLine();
  • 我++;

依此类推,将控制转移到下一个陈述。

循环提出了一个有趣的挑战:

while(x) { M(); }

与...基本相同:

BEGIN: 
if (!x) goto END;
{ M(); }
goto BEGIN;
END: ;

因此端点可以访问。但

while(true) { M(); }

可以优化为:

BEGIN: 
{ M(); }
goto BEGIN;

由于现在无法“到达目的地”,因此该语句被认为具有无法到达的终点。要么永远循环,要么M()永远不会返回,或者M()抛出;无论哪种方式,都不会达到声明的终点。

确定可达性的确切规则比这个草图要复杂一些,但是这可以让你对它们有所了解。 (我喜欢让人们看看他们是否掌握了可达性的挑战是:编写一个程序,该程序具有可访问的goto语句但相应的标记语句是无法访问的.Tricky!)

这些规则在很多地方使用。立即想到三个:首先,开关部分必须没有可达到的终点。其次,非void的方法(或lambda或属性getter等)必须没有可到达的端点。第三,如果方法具有可到达的终点并且它具有out参数,则必须在结束点明确指定参数。

答案 1 :(得分:0)

简单来说,当且仅当语句完成而不执行分支(控制权转移)时才会到达端点。

当退出块的分支是

时,块存在一个不可达的端点
  1. 无条件,或
  2. 存在于所有可能的执行路径中。
相关问题