简体   繁体   English

C#创建类和派生类的实例

[英]C# creating an instance of a class and derived class

I tried the below code in my c# program. 我在c#程序中尝试了以下代码。 This is just for learning the OOPs Concepts. 这仅是为了学习OOP概念。

 class a
    {      
        public void testa()
        {
        }
    }
    class b:a
    {     
        public void testb()
        {
        }
    }

  a a1 = new b();

  b b1 = new a();

I have the following queries regarding the code mentioned above. 关于上述代码,我有以下查询。

  1. Why Im getting error in 2nd line? 为什么我在第二行出现错误?
  2. what is meant by a a1=new b() ; 什么是a a1=new b() ;
  3. why a1.testb() is not accessible even though constructor of b is assigned to a1 ? 为什么即使将b构造函数分配给a1也无法访问a1.testb()
  4. what is the difference between a a1=new a() and a a1=new b() ? a a1=new a()a a1=new b()什么区别?

1) if you mean this line: 1)如果您的意思是这一行:

b b = new a();

it is because every b is a but not every a is b 这是因为每个b都是a但并非每个a都是b

2-3) what is meant by a a1=new b(); 2-3) a a1=new b();是什么意思a a1=new b(); why a1.testb() is not accessible even though constructor of b is assigned to a1 ? 为什么即使将b构造函数分配给a1也无法访问a1.testb()

it means that you create object of b class but get reference to it as a (you can treat it trough this reference without casting only as a even it is b ) 这意味着用户可创建的对象b类,但得到引用它作为a (你可以把它低谷而无需进行转换只能作为参考这样a甚至是b

I change your class and method names to real world equivalents to better understanding. 我将您的类和方法名称更改为现实世界中的等效名称,以便更好地理解。 I name a as Animal , testa as Eat , b as Human , and testb as Talk . 我将a命名为Animal ,将testa命名为Eat ,将b testbHuman ,将testbTalk So we have: 因此,我们有:

class Animal {      
    public void Eat() { }
}

class Human : Animal {     
    public void Talk() { }
}

Animal a1 = new Human();

Human b1 = new Animal();

OK, return to your questions. 好的,返回您的问题。

1) You get error on second line, because every animal is NOT a human. 1)在第二行出现错误,因为每个动物都不是人类。 Is it? 是吗?

2) a1=new b() according to our new naming conventions, turns to a1 = new Human which means Animal a1 = new Human . 2)根据我们的新命名约定, a1=new b()变为a1 = new Human ,这意味着Animal a1 = new Human So, that's correct, because human is a kind of animal. 所以,这是正确的,因为人类是一种动物。

3) a1.testb() according to our new naming conventions, turns to a1.Talk() . 3) a1.testb()根据我们的新的命名惯例,转向a1.Talk() Well, a1 is an animal ( Animal a1 ), and we can not expect an animal to talk. 好吧, a1是一种动物( Animal a1 ),我们不能指望动物说话。

MORE: 更多:

Think a class is a group of attributes and behaviors. 认为一个class是一组属性和行为。 For example, we have a group named Animal that defines an Eat behavior. 例如,我们有一个名为Animal的组,它定义了Eat行为。 And another group named Human that extends Animal group and also it has its own behavior named Talk . 另一个名为Human组扩展了Animal组,它也有自己的行为称为Talk As we know, Human has its super-group behaviors too -eg Eat in this example-. 我们知道, Human有其超级组的行为太-例如, Eat这个例子一样。

When we have an instance of group Animal , we can expect it to eat. 当我们有一个Animal组的实例时,我们可以期望它会吃。 But we can not ask it to talk. 但是我们不能要求它说话。 It's not possible. 这是不可能的。 In the other hand, every item that we choose from group Human , is actually an Animal . 另一方面,我们从“ Human组中选择的每个项目实际上都是Animal So we can ask him to eat. 所以我们可以请他吃饭。

When we have a Human instance, we can ask him to behave as a Human and as an Animal too. 当我们有一个Human实例时,我们可以要求他表现为HumanAnimal I mean, we can ask him to Talk and we can ask him to Eat too. 我的意思是,我们可以请他Talk ,也可以请他Eat Every Human can be located in human group, and in animal group. 每个Human都可以位于人类组和动物组中。

1) When we say Human b1 = new Animal(); 1)当我们说Human b1 = new Animal(); it says exactly: pick up an item from Animal group - right part - and put it in Human group - left part - which is not possible. 它说的很准确:从“ Animal组-右部分中拾取一个项目,然后将其放入“ Human组-左部分中-这是不可能的。 Because there are a lot of animals which are not human. 因为有很多动物不是人类。

2) When we say Animal a1 = new Human : pick up an item from Human group - right part - and put it in Animal group - left part - which is easily possible. 2)当我们说Animal a1 = new Human :从Human组-右部分-拾取一个项目,然后将其放入Animal组-左部分-这很容易实现。

3) When we say a1.Talk() , we expect an Animal to talk. 3)当我们说a1.Talk() ,我们希望Animal说话。 I mean we expect an Animal to act a Human behavior which is not possible. 我的意思是我们期望Animal表现出不可能的Human行为。

Probably inheritance and polymorphism concepts are not so clear for you yet. 对您来说, 继承多态概念可能还不清楚。 This article may help you. 本文可能会为您提供帮助。

If class b inherits from a , you can imagine it as a "specialization" of a . 如果类b从继承a ,你可以把它想象成一条“专业化”的a So you can easily understand that b can be used/seen as an a instance, but the reverse is not true! 所以,你可以很容易地明白, b ,可以使用/视为a实例,但相反的是不是真的!


Why Im getting error in 2nd line? 为什么我在第二行出现错误?

because b b1 = new a(); 因为b b1 = new a(); is not a valid assignment. 不是有效的分配。 As explained, you can assign inherited class instance to base class variable, but not the contrary! 如前所述,您可以将继承的类实例分配给基类变量,但不能相反!

what is meant by a a1=new b(); a1 = new b()是什么意思;

this assignment is correct because you can surely use a more specific class instance as a base class instance. 这种分配是正确的,因为您可以肯定地使用更具体的类实例作为基类实例。

why a1.testb() is not accessible even though constructor of b is assigned to a1? 为什么即使将b的构造函数分配给a1,也无法访问a1.testb()?

when you inherit from a class, all the public and protected methods of this class are inherited and you can access or override that in the new class. 当您从一个类继承时,该类的所有public方法和protected方法都将被继承,并且您可以在新类中访问或重写该方法。 but testb() is not an inherited method. 但是testb()不是继承的方法。 is a new method defined inside class b so you can use it only if you do this assignment: b b1=new b(); 是在类b内定义的新方法,因此只有b b1=new b();以下分配时才可以使用它: b b1=new b();

If you defined a a1 = new b() , to use methods declared in b you can cast a1 as b 如果定义a1 = new b(),要使用b中声明的方法,可以将a1强制转换为b

 a a1 = new b();
 ((b)a1).testb();

Think of your classes as a contract, guaranteeing the existence of certain operations. 将您的课程视为合同,以保证某些操作的存在。 Class a defines one operation, class b inherits all operations from a and defines another one of its own. a定义了一个操作,类b继承所有操作a ,定义了自己的另一个。

The first line: 第一行:

a a1 = new b();

Declares a variable named a1 of type a , meaning whatever value you give this variable should have all the operations type a requires. 声明一个名为的变量a1型的a ,这意味着你把这个变量应该有所有的操作类型的任何值a要求。 new b() creates a new instance of class b , which is assigned to variable a1 . new b()创建类b的新实例,并将其分配给变量a1 Since class b inherits all operations from type a , a value of type b can be assigned to a variable of type a . 由于类b继承了类型a所有操作,因此可以将类型b的值分配给类型a的变量。

On the second line: 在第二行:

b b = new a();

Similarly, you define a variable which should have all the operations defined by type b . 同样,您定义一个变量,该变量应具有类型b定义的所有操作。 But since you put in a value of type a which doesn't define the testb operation type b requires, the compiler doesn't accept this. 但是由于您输入的类型a的值testb类型b所需的testb操作,因此编译器不会接受此值。

As for your third question, the compiler only knows the type of your variable ( a ), not which value you actually assigned to it. 关于第三个问题,编译器仅知道变量( a )的类型,而不知道您实际为其分配的值。 You basically told the compiler "I guarantee this value will define the testa operation. Now let it do operation testb !" 您基本上告诉编译器“我保证这个值将定义testa操作。现在让它执行testb操作!” The compiler doesn't know the actual value of the variable, so as far as it's concerned, that's not possible. 编译器不知道变量的实际值,因此就其而言,这是不可能的。

As for the difference between a a1=new a() and a a1=new b() : In both cases, a variable of type a is created. 至于a a1=new a()a a1=new b()之间的区别:在两种情况下,都会创建类型a a的变量。 In the first expression, the value assigned to this variable is a newly created instance of type a , while in the second, the value is a newly created instance of type b . 在第一个表达式中,分配给该变量的值是类型a的新创建实例,而在第二个表达式中,值是类型b的新创建实例。 Since type 'b' is basically an expanded version of type a , the compiler know that everything you could ask of an instance of type a can also be satisfied by an instance of type b , so it just treats the value as if it is of type a . 由于“B”型基本型的扩展版本a ,编译器知道这一切,你可以问类型的实例的a也可以通过类型的实例满足b ,所以它只是把值,好像它是键入a

1) Every b is an a but the converse is not true. 1)每个b是一个a但反之则不成立。

2) is an example of Polymorphism Polymorphism - Define In Just Two Sentences 2)是多态的一个例子多态-仅用两个句子定义

3) a1.testb() is not accessible because you are treating it as an instance of a which has no definition for testb() 3)无法访问a1.testb()因为您将其视为对testb()没有定义的a的实例

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM