我有以下简单的C#代码,但我不理解输出。

using System;

namespace ConsoleApplication4
{
    class myParent
    {
        public int id = 3;
        private string name = "Parent class private string";
        public void mymethod()
        {
            Console.WriteLine("{0} & {1}", name, id);
        }
    }

    class myChild : myParent
    {
        private string name = "Child class private string";
    }

    class Program
    {
        static void Main(string[] args)
        {
            myChild c1 = new myChild();
            c1.mymethod();
            Console.ReadLine();
        }

        //Output
        //Parent class private string & 3
    }
}


当我调用c1.mymethod()时,为什么要使用string name类中的myParent而不是string name类中的myChild,因为我要在具有定义的myChild变量的string name对象上调用方法?

我曾经相信继承是指将代码从基类虚拟复制并粘贴到派生类,以重用代码或保存按键。但经过一些研究,似乎并非如此。调用继承的方法以某种方式引用了基类,这可能解释了我的代码中的输出。

但是,我仍然不清楚继承的内部工作方式。例如,我从未创建基类的实例。基类方法(myParent.mymethod())应该如何退出?

请帮助澄清我的困惑,并指出一些文档。

最佳答案

当我调用c1.mymethod()时,为什么要使用myParent类中的字符串名称而不是myChild类中的字符串名称,因为我正在对myChild对象调用具有已定义字符串名称变量的方法?


方法c1.mymethod()仅在myParent类中定义。因此,当您调用该方法时,它将使用与该方法最接近的name。换句话说,它将首先在myParent类中搜索该变量,如果找到,它将使用它。

但是,如果您这样做(将myMethod虚拟化并在myChild中覆盖它):

class myParent
{
    public int id = 3;
    private string name = "Parent class private string";
    public virtual void mymethod()
    {
        Console.WriteLine("{0} & {1}", name, id);
    }
}

class myChild : myParent
{
    private string name = "Child class private string";
    public override void mymethod()
    {
        Console.WriteLine("{0} & {1}", name, id);
    }
}


然后它将使用name类中的myChild变量,因为它是最接近的变量。

如果这样做,您将遇到类似的情况:

public class Person
{
    private string name = "John";
    public Person(string name)
    {
        // The parameter is named `name` and the field is named `name`
        // so the compiler is going to choose the closest variable.
        // In this case, it will assign `name` parameter to itself.
        // Visual Studio is nice, in this case, to give you a warning but
        // your code will compile and the compiler will just assign `name`
        // to `name`
        name = name;

        // If you did this: this.name = name;
        // then the private field will be assigned the value of the parameter
    }
}

10-08 01:52