Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/282.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/vb.net/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
我写了一个程序,允许两个类;“战斗”;。不管什么原因,C#总是赢。什么';VB.NET有什么问题吗?_C#_Vb.net_Compiler Construction_Initialization - Fatal编程技术网

我写了一个程序,允许两个类;“战斗”;。不管什么原因,C#总是赢。什么';VB.NET有什么问题吗?

我写了一个程序,允许两个类;“战斗”;。不管什么原因,C#总是赢。什么';VB.NET有什么问题吗?,c#,vb.net,compiler-construction,initialization,C#,Vb.net,Compiler Construction,Initialization,我写了一个程序,允许两个类“战斗”。不管什么原因,C#总是赢。VB.NET有什么问题 static void Main(string[] args) { Player a = new A(); Player b = new B(); if (a.Power > b.Power) Console.WriteLine("C# won"); else if (a.Power < b.Po

我写了一个程序,允许两个类“战斗”。不管什么原因,C#总是赢。VB.NET有什么问题

   static void Main(string[] args)
    {
        Player a = new A();
        Player b = new B();

        if (a.Power > b.Power)
            Console.WriteLine("C# won");
        else if (a.Power < b.Power)
            Console.WriteLine("VB won");
        else
            Console.WriteLine("Tie");
    }
VB.NET中的播放器B:

Public Class B
   Inherits Player

   Dim desiredPower As Integer = 100

   Public Overrides ReadOnly Property GetPower() As Integer
       Get
          Return desiredPower
       End Get
   End Property
 End Class
这是一个基类

public abstract class Player
{
    public int Power { get; private set; }

    public abstract int GetPower { get; }

    protected Player()
    {
        Power = GetPower;
    }
}

当B上的构造函数完成时,两个玩家的私有成员的理论值都将为100


但是,由于C#的高级内部结构,CLI通常认为从该语言编译的整数和其他基本值较高,而从VB.NET编译的值较低,即使它们包含相同的位。

将我的注释提升为答案:

我:

也可以尝试将每个“电源”写入控制台

恶作剧者:

C#:100 VB.NET:0

我:

正如我所怀疑的那样。看起来VB.Net在继承构造函数之前调用了基构造函数,因此VB的desiredPower变量仍然是0,而C#则相反(请记住,文本初始化发生在构造函数的末尾)

更新:
我想找到一些关于行为的信息(否则,你会发现任何新的.Net版本都可能会改变你的行为)。从链接:

派生类的构造函数隐式调用基类的构造函数

基类对象总是在任何派生类之前构造。因此,基类的构造函数在派生类的构造函数之前执行

它们在同一页上,看起来是互斥的,但我认为这意味着首先调用派生类构造函数,但假定它自己在执行任何其他工作之前调用基构造函数。因此,重要的不是构造函数顺序,而是初始化文本的方式


我还发现,这清楚地表明顺序是派生实例字段,然后是基构造函数,然后是派生构造函数。

这里的问题是VB在设置其字段值之前调用基构造函数。因此,基本Player类存储零

.method public specialname rtspecialname 
        instance void  .ctor() cil managed
{
  // Code size       15 (0xf)
  .maxstack  8
  IL_0000:  ldarg.0
  IL_0001:  call       instance void [base]Player::.ctor()
  IL_0006:  ldarg.0
  IL_0007:  ldc.i4.s   100
  IL_0009:  stfld      int32 B::desiredPower
  IL_000e:  ret
} // end of method B::.ctor
这是因为C#首先初始化类字段,然后调用基构造函数。
相反,VB会做相反的事情,因此在VB中将值指定给Power时,private字段尚未初始化,其值为0。

尝试将每个“Power”也写入控制台。该死,你必须告诉我你在C#身上发现所有这些怪癖的秘密。这就是我想投反对票的地方。所以如果人们不能理解问题中的代码。。。他们结束了这个问题。这似乎与堆栈溢出的任务背道而驰。看来构造函数的应用程序顺序很重要,坦率地说,我不知道这一点,并发现这一点很有帮助。我打开这个问题,希望会被冒犯,但后来我读了它。首先它让我笑,然后它让我思考。干得好。如果你查看他的评论,b.Power==0。这是一个笑话:)愚人节快乐:(虽然第二部分很有趣,但前提失败了,因为b.Power是零。但我会收回否决票。
.method public specialname rtspecialname 
        instance void  .ctor() cil managed
{
  // Code size       15 (0xf)
  .maxstack  8
  IL_0000:  ldarg.0
  IL_0001:  call       instance void [base]Player::.ctor()
  IL_0006:  ldarg.0
  IL_0007:  ldc.i4.s   100
  IL_0009:  stfld      int32 B::desiredPower
  IL_000e:  ret
} // end of method B::.ctor