Call derived class from base class (VB.NET) - vb.net

I have created a generic base class for keeping track of open forms (router) of a specific form type that also has a generic base. The problem arises when I need to call a unique derived form method from the derived router class. Is there anyway to do this?
Form router base class has
Dictionary(Of String, Forms)
Derived Form router needs to call unique methods of the derived forms stored in this dictionary. The problem is that visual studio sees the type in the dictionary as the base form class, not the derived form class (but if I do a get type during run time, the object is of the derived form class).
I've tried creating overrideable properties and functions, but the type must be specified in the base class and just using "Object" does not work.
I can post code if need be, but I'm trying to keep this simple and generic.
Thanks!

Cast the value from the dictionary to the derived type:
Dim frmDerivedForm As YourDerivedForm = CType(yourDictionary("yourKey"), YourDerivedForm)
frmDerivedForm.DerivedFormMembers()

Have you tried just casting them? (This is not tested)
Form form;
if(form is DerivedForm)
(form as DerivedForm).DerivedField = "asdf";
Form form;
if(form is DerivedForm)
((DerivedForm)form).DerivedField = "asdf";

Create a protected Overridable (virtual) method in your base class that accepts the data that you need to send to the derived class and returns the data that you need to get from the derived class and then override it in the derived (inherited) class and do what you need.

Related

How to extend derived classes by defining class(es) that exposes the instance as a property

I have a class that I would like to extend by defining a new class that contains the first class as a public property, as well as additional added properties. However, the class that I'm extending has multiple derived types, which should be treated the same in the extension class.
Below is an example of what I am trying to do:
Public Class ClassA
End Class
Public Class ClassB
Inherits ClassA
End Class
Public Class ClassC
Inherits ClassA
End Class
Public Class BaseExtended
Public Property Foo As ClassA
Public Property ExtendedMetaData1 As Double
Public Property ExtendedMetaData12 As Integer
End Class
Public Class DerivedExtendedB
Inherits BaseExtended
Public Property Foo As ClassB
End Class
Public Class DerivedExtendedC
Inherits BaseExtended
Public Property Foo As ClassC
End Class
The code that uses an instance of any of the 'extended' classes would then need use that instance appropriately depending on it's type. There would be many cases where the property 'Foo' needs to be accessed and modified outside of the class that it belongs to.
If I were to implement something like what I have shown above, that would require that I first cast it to the required type before accessing or modifying it. Ideally I would like to do that inside the 'DerivedExtended' class; The alternative, I think, would be to duplicate code to cast that property would [hundreds of times] in the client code.
Private Sub ClientUsesObject(bar As BaseExtended)
' Perform a task that is agnostic Foo type
' Would not require that Foo be cast to any specific type
If bar.GetType() Is GetType(DerivedExtendedB) Then
Dim barCast As DerivedExtendedB = DirectCast(bar, DerivedExtendedB)
' Perform task that requires Foo to be of type ClassB
ElseIf bar.GetType() Is GetType(DerivedExtendedC) Then
Dim barCast As DerivedExtendedC = DirectCast(bar, DerivedExtendedC)
' Perform task that requires Foo to be of type ClassC
End If
End Sub
What I'm looking for is advice outlining or describing a design pattern that can handle this situation. I've searched for quite a while, and have not been able to find any examples that solve this problem.
I realize that this may be somewhat of an "XY" problem. I'm working with existing code that simply assumes all instances are of the same derived type (when in fact some instances are of the other derived type). As such, the existing code does not work. To me what I've tried to outline above seems like the most straightforward path, but I'm open to alternative if this is just the wrong approach.
This pattern of type covariance in derived classes is the canonical reason for what is called in C++ the "Curiously Recurring Template Pattern" and has been called in .NET the "Curiously Recurring Generic Pattern." I believe it's also sometimes referred to as "F-Bounded Polymorphism" (not a computer scientist, so I might have the reference wrong).
You can write a base class like this:
Public Class Base(Of TDerived As Base)
Public Overridable Property foo As TDerived
End Class
And then use it like this:
Public Class MyDerived
Inherits Base(Of MyDerived)
End Class
Then, the derived class has a property foo whose type is MyDerived. No casting required by clients.
However, this has some limitations. It works best when you don't need to switch back and forth between derived and base. There is no one Base, so you can't declare instances of it. If you want to be able to declare something as Base, then you end up needing to fall back on a non-generic base class. This will still work well for certain usage patterns where you don't need to convert from base to derived, but otherwise you run right back into the casting problems you are trying to avoid.
Eric Lippert has written a bit about this pattern. He's always interesting to read, so I'd recommend looking up his commentary.
Another alternative to consider, if the generic approach doesn't work for you, is code generation. You can use T4 templates to process a compact description of what your code should be, and generate the code files from them. A long list of casts is less tedious if you only write the machinery to generate it, you don't write them all out explicitly.

How to read a private attribute of an object without a getter in ABAP

Is there any way to get the value of an objects' private attribute without a getter. Modifying the class is not permitted in any shape or form.
Please find below an example class with a private attribute.
CLASS counter DEFINITION.
PUBLIC SECTION.
METHODS: set IMPORTING value(set_value) TYPE i.
PRIVATE SECTION.
DATA count TYPE i.
ENDCLASS. "counter DEFINITION
CLASS counter IMPLEMENTATION.
METHOD set.
count = set_value.
ENDMETHOD. "set
ENDCLASS. "counter IMPLEMENTATION
How can I get the value of count? Inheriting from counter will not work because count is private, not protected.
Unfortunately not, I have tried this myself in many different ways none of which work:
Having a standard super class - the super class cannot access the
private attributes of subclasses dynamically
Making a subclass will never work since it can only access protected
Attempting to use the unit test framework doesn't work. I tried to
call the kernel modules that allow access to private data but to no
avail.
You are basically flat out of luck. There is one obscure option though depending on the class you are trying to access. Some classes have interfaces specified as friends and if you implement that interface you can access their private data (the ALV on 7.20 is like this) but unfortunately this will only work in a few limited cases.
Runtime type services are the abap's equivalent of reflection.
They allow You nearly to scan every object, and mostly even modify it at runtime. As far as i know, the visibility of attributes does not matter. But be careful.
And read about the various classes, because there are many, each specified to work on a special type of dataopbject ( structs, objects, etc)
http://wiki.scn.sap.com/wiki/pages/viewpage.action?pageId=42965
You could make a sub class, re-implement the setter and set a second variable, then call the parent method. Be aware of the ramifications of having two variables holding the same stuff... Please see vwegert's comments and see if you really want to because it's generally not a great idea and it breaks the rules of OO.
CLASS counter_sub DEFINITION INHERITING FROM counter.
PUBLIC SECTION.
data count2 type i read-only.
METHODS: set REDEFINITION.
ENDCLASS. "counter_sub DEFINITION
CLASS counter_sub IMPLEMENTATION.
METHOD set.
count2 = set_value.
super->set( set_value ).
ENDMETHOD. "set
ENDCLASS. "counter_sub IMPLEMENTATION

Why is 'New' being called for each record retrieved when using the entity Framework

I have been seeing some odd behaviour in an entity that I have for which I created a partial class to override the ToSting Method and provide some basic property setting when a new instance of that entity is created (for example I might set an order date to 'Now') in a constructor.
This odd behaviour led me to look closely at the partial class and I was surprised to see that even when a set of pre existing records was being retrieved the constructor was being called for each retrieved record.
below is a very simple example of what I might have:
Partial Public Class Product
Public Sub New()
CostPrice = 0.0
ListPrice = 0.0
End Sub
Public Overrides Function ToString() As String
Return ProductDescription
End Function
End Class
I have two questions that arise from this:
1) is this normal behaviour in the Entity Framework if you add a partial class to which you add a constructor?
2) if not then I must assume that I have done something wrong, so what would be the correct way to
override the constructor to do things similar to the example I mentioned above?
Thanks for any insights that you can give me.
This is using EF 5.0 in a vb project
think to the sequence of events leading to the retrieval of an entity from the database. Basically it should be something like:
query the database
for each row of the query result give an entity
The giving is then as follow for each retrieved row:
create a new instance of the retrieved entity
populate this new instance with the value of the row
Well with each instance creation, the constructor is called.
I think you are mixing:
instance initialization where you "allocate" the object, and
business initialization where you enforce business logic
both may be done, at least partially, in the constructor.
new is always called when a class is first instantiated and if you do not explicitly declare a constructor then a default constructor will be created by the compiler.
Unless the class is static, classes without constructors are given a public default constructor by the C# compiler in order to enable class instantiation.
When defining POCO classes for Entity Framework the class must have a default constructor and EF will always call this default constructor whether you have explicitly defined it or the compiler did it for you.
If for any reason you have need to pass anything into the class when it is instantiated you can use the ObjectContext.ObjectMaterialized event.

VB.NET - I'm Refactoring and Could Use Some Help

I'm working with vb.net, wcf, wpf and I'm refactoring working code with the hope of being able to reduce some amount of redundancy. I have a bunch of methods that get called in several places throughout the code that only have a slight variation from each other and I would like to replace them with a single method instead.
Specifically, each of the redundant methods process an 1-d array that contain different objects I have created. There are several of these different object types each with different signatures but they have all have a "name" and "Id" property. (Also these objects don't have a shared base class but I could add that if needed.) Each of the redundant methods deal with a different one of the object types.
To refactor the code I would like to pass any of the different object arrays to a single new method that could access the "name" and "id" properties. I'm trying to write this new method in a fashion that wouldn't require me to update it if I created more objects down the road.
I've done some reading on Delegates and Generic Classes but I can't really figure out how this fits in. It would almost be as if I wanted to create a generic class that could handle each of my object types but then somehow also access the "name" and "id" propeties of the different object types.
Any help you can provide would be appretiated. Also, please keep in mind this project is written in VB.net.
Thanks
Mike
It sounds like having your object implement a common interface or have a shared base class would be best. Interfaces give you the most flexibility down the road if you ever need to pass a class to this method that must derive from some other class that does not implement the interface. However, a base class that implements the interface may also be useful just to reduce the duplicate declarations of these properties.
Public Interface IThingThatHasNameAndId 'good name not included
ReadOnly Property Name As String
ReadOnly Property Id As Integer
End Interface
Once you have the interface, you can then pass arrays of types implementing the interface as IEnumerable(Of IThingThatHasNameAndId) or make a generic method taking T() and constrain T to the interface.
Make a base class with the Name and ID properties, then you can make a method that takes in any class that derrives from that class.
Public Function TestFunction(Of t As YourBaseClass)(Byval obj As t) As Boolean
If obj.Name = "Some Name" AndAlso obj.ID = 1 Then
Return True
Else
Return False
End If
End Function

How do I treat two similar types as one?

In VB.NET, I am trying to talk to a webservice (that can't be changed) to create and update customer data.
The CreateCustomer service expects an object of type ConsumerPerson and the ChangeCustomer service expects an object of type ChangeData.
The properties of these two object are exactly the same, so I thought it would be wise to just set the properties using one single function.
However, I am unable to find a way to tell my function that I want to fill either the ConsumerPerson or the ChangeCustomer object.
How do I make this work without late binding problems?
An interface sounds like your best approach. Here is a short code snippet. I picked a simple property named "Name" of type string. It should be easy to modify with the actual properties on your class.
Public Interface ICustomerData
ReadOnly Property Name As String
End Interface
Public Class ConsumerPerson
Implements ICustomerData
Public ReadOnly Property Name As String Implements ICustomerData.Name
Get
return _name
End Get
End Property
End Class
Public Class ChangeData
Implements ICustomerData
Public ReadOnly Property Name As String Implements ICustomerData.Name
Get
return _name
End Get
End Property
End Class
use an interface !
declare an interface IFoo, and implement its members in your subclasses ConsumerPerson and ChangeCustomer. That's exactly what interfaces are for.
You create an interface which both classes implements.
Is it not possible to overload your function with the second data type?
If you cannot change your objects, but they share the same field names, you could xml serialize the data and deserialize as the other class. - You should strongly consider the performance implications of this; however, it would give you the functionality you're asking for.