Parent
public class ParentMap : Map<Parent>
{
public ParentMap()
{
DiscriminateSubClassesOnColumn<string>("Provider").Nullable();
}
}
Children:
public class Child1Map : SubclassMap<Child1>
{
public FacebookAccountMap()
{
DiscriminatorValue("child1");
}
}
public class Child2Map : SubclassMap<Child2>
{
public FacebookAccountMap()
{
DiscriminatorValue("child2");
}
}
from service i get instance of Parent but with property item.Provider equal to childOne, how can i get instance of Child1 or Child2 based on value of proprty Provider ?
Your question I'm afraid isn't completely clear, but I'm going to take a guess:
Most likely you don't receive instances of Parent, but instances of ParentProxy, a class that NHibernate generates that inherit from Parent. This class cannot be cast to Child1, but the instance will in fact contain an instance of the Child1 class. Methods calls are forwarded to this contained class. This mechanism is part of NHibernate's lazy load system - since NHibernate needs to create the proxy object without loading the full object data, it doesn't know which exact type to use.
This scenario will happen if you get the instance by following a reference from some other class.
The idea is normally that:
You normally shouldn't need to cast. If you need to cast from base class to subclass you haven't succeeded in creating a good object oriented design and you should explore methods to avoid the cast (since the inheritance structure implies that the caller shouldn't need to care about the actual subclass, the need to cast violates this principle and should therefore be avoided when possible).
If you really must access the true Child1 instance, you could provide an As<T>() method in the base class.
Related
I have two sequences of objects 'A' and 'B'. Comparing the sequences should produce a third sequence 'C' of elements that indicate whether:
the objects were "deleted" from 'A' or
"inserted" from 'B'.
All remaining elements are considered as "matched".
What I would like to do:
Declare Inserted<T>, Deleted<T>, and Matched<T> generic classes that inherit all their properties from the T base class. The generic class must be able to instantiate itself from the object it inherits.
The code:
public interface IInstantiable<T>
{
void CopyFrom(T o);
}
[Serializable]
public class Inserted<T> : T
where T : IInstantiable<T>
{
public Inserted() { }
public Inserted(T t)
{
this.CopyFrom(t);
}
}
The error:
'MyNamespace.Inserted<T>' does not contain a definition for 'CopyFrom' and no
extension method 'CopyFrom' accepting a first argument of type 'MyNamespace.Inserted<T>'
could be found (are you missing a using directive or an assembly reference?)
Further discussion:
I define my own IInstantiable interface to enforce the existence of a CopyFrom method. I cannot use the standard ICloneable interface, because it only defines a method that copies the object to a new instance, whereas I need the object to copy its members in the constructor.
The error goes away if the generic defines its own implementation of the CopyFrom method; however, this does not achieve the desired goal of specializing the CopyFrom method to handle the specific needs of the base class. Only the base class could know what properties should be copied. (Or am I missing something?)
Note: The final object should have the same public members as its base class, as the object should be capable of serialization.
Is this possible in .NET?
The answer:
What I am attempting to do is impossible, simply because the generic class cannot be an extension of the template base class. Visual Studio complains "Cannot derive from 'T' because it is a type parameter." (I hadn't noticed this error yet because I had not implemented the CopyFrom method in the generic class yet.)
If I were to change the interface into a class and supply a stub implementation in that class, I could inherit from it as suggested below; however, this introduces a new base class into my inheritance hierarchy.
public class IInstantiable<T>
{
public virtual void CopyFrom(T o) { }
}
[Serializable]
public class Inserted<T> : IInstantiable<T>
where T : IInstantiable<T>
{
public Inserted() { }
public Inserted(T t)
{
base.CopyFrom(t);
}
}
Unfortunately, I cannot use this new base class in its templatized form because I must introduce it at the root of my inheritance hierarchy. It works only if I remove the template and make it as generic as possible.
public class IInstantiable
{
public virtual void CopyFrom(Object o) { }
}
However, this still does not make my Inserted<T> generic look like the object it is initialized from, and since I cannot inherit from the same type as the type parameter, it does not suit my initial purpose.
Moving away from "fancy generics" based on the type system to more (ahem) generic annotated structures might prove to be the best solution; however, the default behavior of my selected serialization approach (XmlSerialization) does not have the automatic support that would make this configuration a viable solution. Generics will not work; use hard-coded class definitions instead.
This is indirectly what you're trying to declare in your code above.
[Serializable]
public class Inserted<T> : IInstantiable<T>
where T : IInstantiable<T>
{
public Inserted() { }
public Inserted(T t)
{
this.CopyFrom(t);
}
}
Does this make sense?
.NET doesn't allow you to inherit from a generic parameter. How could it? Generics are evaluated at runtime but it needs to know what type your class is at compile time.
If I understand correctly, you want to annotate a sequence of objects with the notion of what their state is (inserted, deleted, or matched).
You don't really need fancy generics for this; what's wrong with:
enum ChangeState { Inserted, Deleted, Matched }
struct<T> Annotated {
public T Obj;
public ChangeState;
}
You can mark this for serialization however you want (the Annotated object can serialize just fine without the same properties/fields).
Though you can encode more information in the type system, it's unclear to me what the benefit would be here. Are you sure you want to do that?
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.
I have a category/file tree structure. Both categories and files can have parents, so I derived them from a common base class that has a Parent property. Since all parents will obviously always be categories (files can't be a parent), it seems to make sense to make the Parent property of the node be the CategoryNode type.
Is it bad form for the base class to refer to the derived class? If so, why? What's a better way to structure this, if so?
class Node {
public CategoryNode Parent {get; set;}
}
class File : Node {
...
}
class CategoryNode : Node {
...
}
You could do ...
interface IParent {
...
}
class Node {
public IParent Parent {get; set;}
}
class File : Node {
...
}
class CategoryNode : Node, IParent {
...
}
This way, you don't need to refer to a derived object in the base class, plus, you're more flexible in what can actually become a parent, in case you get additional object types at a later point in time. Also, any functionality that is relevant just for a parent can be declared in that interface.
If the property Parent is actually a common properties of all descendants and always of kind CategoryNode, it's not a problem. Semantically speaking it's correct and technically I think its correct too as soon as you remain in the same library (to avoid circular references).
This can be a problem when you write code like this :
// BAD CODE
if(myProp is subclassA)
{ ...
}
else if (myProp is syubclassB)
{ ...
}
This code is bad, because you loose the advantage of inheritance.
Even in the .Net Framework there is such constructs. The first example that comes in my mind is the XObject.Parent property.
XElement inherits XObject, and XObject publish a property of type XElement. Same as your snippet.
The base class shouldn't know who derives from it.
If you have such a case, you probably dont want inheritance. You should just use some form of coupling.
The File and CategoryNode should hold a Node member in your case.
Other options will be to change class hierarchy to make the CategoryNode a root class (a), or change the property type to Node (b).
Both of these possibilities are not good:
(a) File will have all functionality CategoryNode has which it doesn't need.
(b) It will hide object type (which is always CategoryNode). This may follow to invalid cast errors somewhere else in your code. For example, if you forget there is always a CategoryNode instance.
Considering this, I believe current code is OK.
As stated above, is it redundant to inherit from Object in c#?
Do both sets of code below result in equivalent objects being defined?
class TestClassUno : Object
{
// Stuff
}
vs.
class TestClassDos
{
// Stuff
}
I snooped around on MSDN but wasn't able to find anything perfectly conclusive.
If left unspecified every class definition will implicitly inherit from System.Object hence the two definitions are equivalent.
The only time these two would be different is if someone actually defined another Object type in the same namespace. In this case the local definition of Object would take precedence and change the inheritance object
namespace Example {
class Object { }
class C : Object { }
}
Very much a corner case but wouldn't point it out if I hadn't seen it before
Note that the same is not true if you used object instead of Object. The C# keyword object is a type alias for System.Object and hence it wouldn't match Example.Object.
namespace Example2 {
class Object { }
class C : Object { } // Uses Example.Object
class D : object { } // Uses System.Object
}
Of course if you have a truly evil developer you could still cause confusion with object
namespace System {
class Object {
private Object() { }
}
}
namespace Example3 {
// This will properly fail to compile since it can't bind to the private
// Object constructor. This demonstrates that we are using our definition
// of Object instead of mscorlib's
class C : object { } // Uses our System.Object
}
Yes, everything ultimately inherits from an object if defined as class. Leave the explicit inheritance out of your code.
Yes it is redundant to inherit from object in class
MSDN : Object class : 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.
Check this research : inherits from object? An investigation into how.
Object is the mother of all classes in .Net. There is nothing above it.
All classes inherit from it. So this code
class TestClassDos
{
// Stuff
}
automatically means it is inheriting from object.
Proof: You can typecast any entity to object which is possible if it is inheriting from it.
Summary of Object class says
// 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.
Yes, they are both the same thing, I don't think I saw anyone mention structs, but all objects (that is regardless if you declare a class or a struct) they all ultimately inherit from Object, see this Object MSDN article and this other article on Structs
There is a time when inheriting from object makes sense — when you have a partial class definition, and you want to lock down inheritance and prevent other partial declarations from extending a different class. Attempting to inherit from another type in the partial class will then give you the CS0263 Compiler Error.
This only makes sense in the event that your partial class is not already inheriting from another type.
The partial keyword is not in your code example, but I thought it might be worth mentioning as I found my way here from Google after seeing a similar setup in an API. Aside from inheriting from objects that don't point to the official System.Object as others pointed out, there is no benefit in doing so as all classes inherit from object implicitly.
I have a child and a parent class, as such:
class B : A{
public B : base(){
// stuff
}
}
class A{
public A(){
// how can I gain access here to the class that called me,
// ie the instance of class B that's being instantiated.
}
}
As above, my question is whether I can see who called the parent constructor within the constructor of the parent class.
One way to do this would be to have a separate function in A to which you pass this from within B. Is there anything simpler, ie can I do this during object initialization, or is that too early in the object construction process ? Does the whole object B need to be "ready" before I can access it from within A ?
Thanks!
Within A, it's easy - you just use this and cast it to B if you're confident that it really is a B rather than any other derived class. The object will already an instance of B.
However, it's generally a bad idea to call virtual methods from constructors, as the body of the B constructor hasn't been run yet, so it's only half-initialized. I've had a few situations where this is a pain, but if you tell us what you're trying to achieve we may be able to come up with something cleaner.
You can check what the type is which is being instantiated:
public A()
{
var theType = this.GetType(); // will be typeof(B) in your example
}
But acessing the instance (e.g. it's properties) is probably not wise, since the derived type is not yet initialized when the base type's constructor is executing.