I'm confused about how object allocation is done in the case of inheritance
consider the following code.
class Base
{
}
class Derived : Base
{
// some code
}
and from main if we do
Derived d = new Derived();
and
Base b = new Derived();
what is the memory allocation of both cases in the heap.
Is the derived object in inside base object or they both are beside each other
Memory allocation for both objects will look exactly the same. Both objects are of the same type Derived.
Of course, each object will be allocated in its own space on the heap.
What counts when creating objects is the class (type) used to construct the object, not the type of reference where object will be stored.
Each object exists as complete entity, but you can look at it as summary of all parts from all the classes it inherits from. In a way Derived object instance contains Base object instance inside. Not the other way around.
In both cases you instanciate objects of the concrete Derived class, so the memory footprint would be the same for both - you refer to them using references of the Base and the Derived class, but you instantiate the Derived class in both cases.
But as to providing a general answer to your question - yes, in memory instances of derived classes contain all the members of their base classes.
Related
consider the following code:
class Base
{
}
class Derived : Base
{
// some code
}
and from main if we do
Derived d = new Derived();
I have two questions:
Q1-We know when we do new Derived();CLR allocate a Derived object in the heap. But since Derived derives from Base, Derived implicit constructor also calls Base's implicit constructor, does it mean that there is also a Base object allocated in the heap?
Q2-(if the answer to Q1 is true) In GC's context, we refer to all reference type variables as roots. So for example, variable d is a root, and this root points to Derived object only. Here is a problem, there is no root variable to Base object, in theory Base object is always marked as unreachable by Garbage Collector and then get swept. which is obviously not correct, so does it mean that an implicit root variable will be assigned to Base object to keep it reachable?
You've misunderstood the nature of inheritance. There is just one object created here, an object of type Derived. The inheritance means that Derived gains some properties inherited from Base, but that does not mean another object of type Base is created. So to Q1, the answer is no. Therefore there is no need to answer Q2. The GC has one memory allocation to track, that for Derived.
When you create a new instance of a derived object (e.g. Derived d = new Derived();), a single object is allocated, not separate objects for the derived class and its base class.
Imagine they were both structs and you had to compose the derived object manually. You might end up with something like;
public struct Base {
...
}
public struct Derived {
public Base base;
...
}
The memory required for Base is contained within the memory footprint of Derived.
I'm working with an API, and I created my own wrappers with interfaces derived from some of the classes defined in the API.
I'm trying to copy the values from a base object into a derived object without overwriting the derived object's derived members.
This is what I'd like to attempt:
List<DerivedClass> derivedObjects = new List<DerivedClass>
{
new DerivedClass(randomVar),
}
// baseObject.Foo() returns a base class object, I want it to populate all the
// base class members of my derived object without modifying the derived members
derivedObjects[0] = baseObject.Foo(derivedObjects[0]);
Unfortunately, this is the way the API works, I have to pass in an instantiated derived or base object, in order to get back the "same" base object but further populated with certain things I need.
Any idea how one could go about this?
I need to clarify a thing that how an object type variables accept class type instance an given in the below code snippet,
class MyClass
{
}
static void Main()
{
object obj = new MyClass();
}
Since the MyClass is not a type of object but still the instance of MyClass is accepted in the obj(object) variable.
Actually, your class is an object.
In C# all classes derives from object.
Referring to a class as it's base type is one way of Polymorphism.
It might be better understood using an analogy:
Your class is an object, like a Dog is an animal.
Also, If you try the following:
object obj = new MyClass();
bool isMyType = obj == typeof(MyClass); //<--this will be true.
Take a look at this SO thread for more information how Polymorphism can be useful.
The concept that you do not understand is polymorphism which basically say that you can define an is relation between your classes. For a simple logic every dog is an animal so you can have class Dog that inherits from Animal. This implies that you can assign to variable of type Animal an instance of a Dog but not the other way around - not every animal is a dog. Another thing is that every thing derives form object this is language concept that you simply can take for granted.
Evrything in c# is derived from Object...
even your class.
.Net follows OOPs (Object Oriented Programming Language) and here every class can act as a object. Every class inherits Object class and hence every class can act as an object. In your example, .Net creates a default constructor to create instance of the class. You can definitely write your own constructor there.
Hope it helps.
Everything in C# is derived from Object.
Even Value Types like struct(int,float,..) are all derived from Object type.
When you define your own class,it implicitly derives from the Object type.
It is mentioned in the docs
All classes, structures, enumerations, and delegates inherit from
Object class
MSDN:
Supports all classes in the .NET Framework class hierarchy and provides low-level
services to derived classes. This is the ultimate base class of all classes
in the .NET Framework; it is the root of the type hierarchy.
Inheritance Hierarchy:
All classes, structures, enumerations, and delegates.
This means when you use int.Parse() to cast some value to int, there is a class behind int type which makes it able to have methods and do such stuffs. Object has been rooted pretty much everywhere in .Net.
I have a three classes A, B, and C shown below
public class A
{
public void add(int i, int k)
{
}
}
public class B:A
{
public void AddInt()
{
add(1, 2);
}
}
public class C
{
public void AddInt()
{
A objA = new A();
objA.add(1, 2);
}
}
We want access the "A" class method Add, there are two ways
1) Initiate the "A" class, then access the Add method
2) Inherit the "A" class, then access the Add method
If both those ways provide the same functionality, then why does C# provide two ways to achieve the same functionality.
What is the difference between initiating a class and inheriting a class?
First off, the word you're looking for is instantiate, not initiate.
What is the difference between instantiating a class and inheriting a class?
Inheritance expresses the "is a kind of" relationship between two classes:
The New York Times is a kind of newspaper.
A giraffe is a kind of animal.
An apple is a kind of fruit.
In each of these cases the first kind of thing is the "more derived" type -- it is more specific -- and the second thing is the "less derived" type, or "base" type. It is more general. More things are fruits than are apples.
In C# when you establish an inheritance relationship between two classes, you get two things:
Assignment compatibility: you can use an expression of the more derived type where an expression of the base type is needed.
Member inheritance: all methods, events, indexers, operators, fields, properties and nested types of the base class are automatically members of the derived class. (Constructors and destructors are not inheritable).
Instantiation is the process of making a new instance of a type.
Here, let me give you a copy of today's New York Times.
Here, let me give you a giraffe.
Here, let me give you an apple.
So in C#:
class Fruit {}
class Apple : Fruit { } // Apple inherits from Fruit
class Program {
static void Main() {
Apple apple = new Apple(); // Instantiating a new Apple
}
}
Make sense?
It's not about C# at all, it's about basic OOP concepts, that C#, in this case, simply manifests, being object oriented and strong typed language.
"Initialization" is a creation of an instance of a given type: A in your case.
Second example is a Polymorphism , where you derive from a given type A, and creating derived type B, is able to access public/protected members of the A class.
The access behaviour is the same in this case, but origin of that is completely different.
you are comparing Humans with food ... right no comparison
Initiating cost you some RAM of your system.
Inheriting lets you enable reuseability of common code
These two ways are available because your add method is public in class A. Change it to protected if you want to use it only in inherited classes. Simply saying inheritance makes all properties and methods except of private ones available in inherited classes. In your case class B is inherited from class A and instance of class B itself would be your instance to call method add on. In class C you simply created an instance of class A and called method add on it. All of this concepts would be much cleaner to you if you'll read about Access Modifiers and Inheritance.
Think of a class as a template, or plan, for how to build something. When you then use the template or plan to build one (think of architect plans for a house, and one of the many houses built from those plans), the words we use to describe this process are "Instantiation" and "Initialization".
You instantiate an instance of the object (build the house) using the class template (architects plan), and then initialize it (paint and decorate the house).
Inheritance, on the other hand, refers to something completely unrelated, in how classes are defined, using another existing class as a foundation or *base*line from which to start the definition of a new class that will extend the foundation or base class. When one class inherits from another, it means that "instances" of the derived class automatically get all the stuff that was defined in the parent base class without having to redefine it in the child.
A class is a type and acts as a template that allows you to create objects of this type. The creation of such objects is also called instantiation. This instantiation process involves allocating memory for this object (allocation) and then initializing this object, i.e. give its fields initial values. The latter is called initialization.
Inheritance is something completely different. Inheritance is about creating a new class (template) by inheriting existing code from a base class (also called superclass, or parent class).
This new derived class (also called subclass or child class) serves as template for the creation of a new type of objects.
The derived class can modify the behavior inherited from its base class and extend its possibilities. Inheritance creates a relation between the classes. Subclasses are assignment compatible with the superclasses above them in the inheritance hierarchy.
When you derive from a class and instance the subclass, the runtime also instances the super class, right?
Since abstract classes can't be instanced, are they not created by the runtime when a subclass is instanced?
If so, then abstract class inheritance would be faster than normal class instance?
The runtime never creates separate instances of the base class and the derived class - it's just that the derived class instance also has all the variables etc of the base class, and runs the base class constructor as part of initialization. There's no difference here between "normal" base classes and abstract base classes.
I think you have some details confused.
When you construct an object, where the class of that object inherits from another class, it's not like you get two objects in memory.
You only get one, but it has space set aside for fields that comes from both.
Put another way, if the original class needs 10 bytes to hold its fields, and your inherited class needs 5 bytes to hold its specific fields, when you construct an object from your inherited class, it would occupy 15 bytes, where the first 10 corresponds to the fields from the base class. (note, this is a very simplified explanation, there's a lot more going on that dictates the actual size of objects).