How to hide methods from base class? - c#

I use Castle Active Record' ActiveRecordBase class as a base class for my db objects. That allows me to take advantage of the AR pattern goodies, like:
MyClass clas = new MyClass();
clas.Number = 5;
clas.Save();
The problem is, for some objects, I want to hide these methods. How can I do that? I don't use interfaces for these objects.
Edit1:
To make it more clear: I want to have 10 classes inheriting from the base one, but 3 of them shouldn't expose some of the methods from the base class. So for example for MyClassB, this:
MyClassB clasB = new MyClassB();
clasB.Number = 5;
clasB.Save();
shouldn't be possible - this object SHOULDN'T be able to Save().
Edit2:
I've read c# hide from dervied classes some properties of base class . I agree that this is bad approach, but bear in mind that I have to use ActiveRecordBase, which I cannot simply modify (at least if I want to stick with the original Castle Active Record sources).

You don't do this.
You restructure your design so that the 7 objects inherit from one object that provides the functionality they want, the other 3 inherit from one that doesn't provide this, and they all inherit from the main "core" object. Think of it like a tree. Instead of trying to hide leaves from view, you simple change the location of the branch. I'm not sure this analogy works, but lets pretend it does.

If you want to hide them, the probably do not belong in that base class. I suggest expanding the inheritance hierarchy to achieve this.

Related

Inheriting Or Creating Static methods is better in this case?

I have a Common class
say
Public class Trans
{
//Access modifiers like the following 20 are there and 20 methods
protected internal string TopVenueCd
{
get { return this.Ticket.GetValue("venueCd", "").TopOne().GetStringValue(); }
}
}
I am inheriting this class to where ever i need.
But in that in all the classes where i am inheriting i dont need all methods.
So I can create that as a static class and access it where ever it is required..
Which is wiser ?
And please give reasons for that as i am not clear in depth in oops in performance..
Thanks for all replies..
UPDATE
My Aim is to segregate one Collection related process separately in a class.
( I am using mongoDb ) One Important Collection which is heavily used and it s a big one with nested document.
Still the schema is not fixed and freezed. Still working on it to get a better solution.
So if i take the logical manipulation of that particular Collection separately in a class, if i change the schema i can change only this class.That is intention.
Since i m a beginner in C#, oops this question arise..
How to do this segregation well in best practice ?
Inheritance is so much misused as a "copy stuff into my class"-feature. It should be used for real inheritance situations (is-a-relation).
If static methods work as well, definitively use that. Use extension methods to make your static methods easy to find.
Why?
Because inheritance is the much higher coupling. You couldn't easily decouple it by using interfaces and injected services in the future.
While you can access static methods from many helper classes, you can only have one base class. If you need more stuff in the future, your base classes will become too big. Because you always inherit everything, all your classes become too big.
When you need a base class for real inheritance in the future, you can't give your class another base class anymore.
Therefore, simply do not use inheritance if in doubt. There are rare really good applications of inheritance.
There might be a problem with your design if you need to inherit a class when you don't need all the methods.
It might be that your base class is a God object, and it has too much responsibilities, or that you have lumped up a few non-essential functionalities into a common base, which is a violation of the Interface Segregation Principle.

How to configure the factory to generate the object?

Maybe the title is not so clear. Let me clarify what I'm trying to accomplish.
I have to base classes:
BaseProperties
BaseProblem
BaseProperties contains data about the generation of math problems. For example, in the image above, BasicAdditionProperties contains Addend1 and Addend2, this two objects know about the range of the generated value to represent a BasicAdditionProblem.
So, this is just an idea.. I guess I supposed to pass the abstract class to a factory, and this one should generate the problem (in this case BasicAdditionProblem).
I have read, it's recomended pass these values as the base class. And my main doubt is, when I pass the object BaseProperties to the factory, all the time do I have to cast the object?
Or what ideas can I implement to model this scenario? Or do I have to have a static Factory where maintain and be used as mapping to the concrete factories?
Thanks in advance.
Define an abstract CreateProblem() in the BaseProperties class. This method can be used generically to allow each concrete Properties subclass to provide its own Factory method.
This is similar to using an instance of WebRequest subclass and calling GetResponse() on it and it then returns the coresponding subclass of WebResponse.
This distributed abstract factory approach allows you to add property/problem pairs easily to the system because the code to map the two is solely contained in those two classes.
You could also use a full Abstract Factory implementation where you have PropertyProblemFactory that defines a CreateProperties() and a CreateProblem(). So in your example you would have AdditionFactory that knows how to create the matching set. But this forces you to define an additional class for each Property/Problem pair. It also works best when you have a class that uses the current/selected PropertyProblemFactory, creates a Properties with it, and then immediately uses that same PropertyProblemFactory factory to create the matching Problem. Once you let go of the reference to the factory and solely have just a reference to the Properties, it is harder to re-locate the right factory to create the Problem. (This can be addressed with yet another class to map object types to factories, but the complexity rises. So the first appoach I suggested is better in this kind of situation).
There are multiple solutions for this. It just depends on how you want to program it.
abstract methods in the abstract class must be handled in all classes that inherit from the abstract class. This way you can easily call abstract methods in the factory without casting.
However when you need to use lots of data from just one specific class then it would not be wise to make abstract methods for it and you should just simply cast the object.
So it all depends on how much classes inherit from BaseProperties and how much data in those classes are the same.

Can I instance a class that inherits the values of an instance of a superclass?

I am using C#, but I think this is a pretty generic OO question. Suppose I have a class called Animal, and it has properties like LegCount, EyeCount, HasFur, EatsMeat, etc.
Let's say I have an instance a of Animal. Suppose a has LegCount set to 4 and EyeCount set to 2.
Now, I'd like to create an instance d of type Dog, which inherits from Animal. I'd like to initialize d with all the values of a. I realize I could create a constructor or otherwise some other method that would take an Animal and spit out a new Dog with all the values copied in, but I was hoping there was some Object Oriented principle / trick that had me covered.
What I want to do, in plain English, is:
Create new Instance d of Dog, with all starting values from a. The key is "all", as opposed to specifying each property individually.
When you design a class that inherits from some other class, you don't need to list all the members it inherits. It just inherits all of them. So I am wondering if I can "inherit the values" on actual instances.
The feature you want is called "prototype inheritance" or "prototype-oriented programming". C# does not support this feature, so you're out of luck there.
You might consider using a language that supports prototype inheritance if your architecture fundamentally needs this feature. JavaScript is the most commonly used prototype inheritance language.
Prototype inheritance can be quite tricky to get correct if you're not careful. If this subject interests you, see my article on some of the bizarre situations you can run into with prototype inheritance in JScript:
http://blogs.msdn.com/b/ericlippert/archive/2003/11/06/53352.aspx
You can't do what you're asking for with some C# language construct, you have to manually write mapping or delegating code. Or, take a look at AutoMapper for that.
You could try a different approach with using the decorator pattern? An alternative to subclassing for extending functionality. Then all your values in the Animal class instance is preserved
http://www.dofactory.com/Patterns/PatternDecorator.aspx
public class Animal
{
public Animal(Animal otherAnimal)
{
if (otherAnimal == null)
throw new ArgumentNullException("otherAnimal");
foreach (System.Reflection.PropertyInfo property
in typeof(Animal).GetProperties())
{
property.SetValue(this, property.GetValue(otherAnimal, null), null);
}
}
}
and then just call this Animal constructor from your Dog(Animal otherAnimal) constructor
But still you should to think over one more time about design of your classes and make Animal an abstract class. Because what do you imagine as instance of class Animal..

Invalid Cast from UserControl to custom control

I have several controls that all inherit from UserControl, and I have a MergeSort method that runs on UserControl types (to save me from writing out 6 different methods), but when I cast back to my custom controls after the sorting, it throws an error, what am I doing wrong? The mergesort method requires the Left property, which each custom control uses, so is there any other way I can do this?
MergeSort method looks like:
public UserControl[] MergeSort(UserControl[] array)
Cast looks like:
(CustomControl[])MergeSort(customControlArray);
I think you have to cast each of them manually:
CustomControl[] customControlArray;
...
UserControl[] sortedControls = MergeSort(customControlArray);
CustomControl[] sortedCustomControls = Array.ConvertAll<UserControl, CustomControl>(sortedControls, delegate(UserControl control)
{
return (CustomControl)control;
});
If you have .NET 3.5+ at your disposal you can use much "cooler" syntax. :)
Edit: the cooler syntax is:
UserControl[] sortedControls = customControlArray.ToList().ConvertAll(c => (CustomControl)c).ToArray();
:-)
(I deleted my previous answer because I think it was actually incorrect.)
It sounds like you need an abstraction between your controls and UserControl which represents common functionality. There are two main ways to accomplish this, and whichever one you use is a matter of personal coding preferences, how you plan to extend these further, how you organize your code in the project, etc...
Inherit from a base class. Basically, create a MyCustomControl (or whatever you want to name it) class which implements the common functionality between your custom controls. This would inherit from UserControl and your controls would inherit from this. Then your method would expect/return an array of this base class.
Implement an interface. You could create an ICustomControl (or whatever you want to name it) interface which represents the common functionality between your custom controls. Then your controls would inherit from UserControl as well as implement ICustomControl. Then your method would expect/return an array of this interface type.
I personally prefer the interface approach. Inheritance tends to be overused in a lot of people's object oriented code, and really shouldn't be. An interface better represents an abstraction (or code contract) as a type (as opposed to a class). But that's a much bigger discussion debate for another time, I suppose :)

Can I use Extension Methods to implement an Interface?

I would like a class to implement an interface, I do not want to change the original class (that would add undesired dependecies).
I know I could inherit from the class and make it's child implement these methods, but then I am faced with a problem how to convert the parent class (that come from the data / ORM) to this presentation class.
If I implement all the interface required methods, will it count as being that interface or not ?
No, it still won't count as implementing the interface.
Extension methods are nothing more than a way of calling static methods in a different kind of way. They don't affect object identity, inheritance etc at all.

Categories

Resources