在C#中具有未定义行为的代码

在C ++中,有很多方法可以编写编译代码,但会产生未定义的行为(Wikipedia) 。 在C#中有类似的东西吗? 我们可以编写C#编译的代码,但有未定义的行为?

正如其他人所提到的,“不安全”块中的任何东西都可以产生实现定义的行为; 滥用不安全块允许您更改构成运行时本身的代码的字节数,因此所有投注都closures。

整数除法的转angular情况具有实现定义的行为。

抛出一个exception,从不捕获它导致实现定义的行为 – 终止进程,启动一个debugging器,等等。

在C#中还有一些其他情况,我们被迫发出具有实现确定行为的代码。 例如,这种情况:

http://blogs.msdn.com/ericlippert/archive/2006/04/06/odious-ambiguous-overloads-part-two.aspx

但是,安全,行为良好的C#程序具有实现定义的行为的情况应该是非常罕见的。

是! 即使在安全的情况下也是如此! (嗯,它的实现定义为至less未定义)

这里有一个来自Marek Safar和VSadov的Roslyn问题 。关于bool ,C#和CLI之间是不匹配的。

C#认为只有一种是true ,一种是false

CLI认为false是一个包含0的字节,其他所有值都是true

这种差异意味着我们可以强制C#做一些 (边缘)有趣的事情

 //non-standard bool //We're setting a bool's value to a byte value of 5. var a = new bool[1]; Buffer.SetByte(a, 0, 5); //non-standard bool //We're setting a bool's value to a byte value of 10. var b = new bool[1]; Buffer.SetByte(b, 0, 10); //Both are true. Console.WriteLine(a[0]); Console.WriteLine(b[0]); //But they are not the same true. Console.WriteLine(a[0] == b[0]); 

以上输出:

true

true

false

有趣的是,debugging器不同意(必须以不同的方式评估真相?)

在这里输入图像说明

无论如何,C#团队的结论似乎是(强调增加):

IE语言将会完全不关心非标准的布尔。 特定的实现(如CIL上的MS C#)将会承认非标准布尔的存在,并将其行为规定为undefined

看看Wiki,未定义的行为发生的情况是不允许的,或者在C#中抛出一个exception。

然而在不安全的代码中,我认为这是不可行的,因为这样可以使用指针等。

编辑:它看起来像我是正确的: http : //msdn.microsoft.com/en-us/library/aa664771%28VS.71%29.aspx

有一个未定义的行为在c#中的例子

根据ECMA-334文件(p。473):

不包含任何不安全修饰符的程序不能显示任何未定义的行为。

这促使“实施定义”到最坏的情况,请参阅Eric Lippert的回答。

许多子程序的要求可以概括为:

  1. 给出有效的数据时,产生有效的输出。

  2. 即使有无效的投入,也不要发射核导弹,否定时间和因果关系的规律。

Java和.NET语言的主要devise目标之一是,除非代码使用某些被标记为“不安全”的特定代码,否则通常不需要特别的努力来满足上述第二个约束[尽pipe一些行为与垃圾收集和Finalize从时间/因果的angular度来看可能有点怪异,这些可以被描述为正常的因果规则的例外,而不是全部的撤销。 这种情况与C中的情况有很大的不同,在这种情况下,许多与数据相关的错误(例如整数溢出)可能导致编译器以任意方式运行,包括做出任何必要的假设以避免溢出。 超现代C哲学所鼓励的真正可怕的未定义行为,不存在于“不安全”块之外的C#或其他.NET语言中。

总的来说,我会说不。

在初始化之前使用自动variables。

所有variables都必须初始化。 如果没有发生exception。

被零除

抛出exception。

索引数组越界

抛出exception

正如Aequitarum Custos指出的,你可以使用不安全的代码。 然后再次这不是真正的C#,你明确地select了C#环境。

实际上并不是维基的意义上的,但是我想我想到的最明显的例子是简单地写一些线程代码,但是在任何语言中都是这样的。