Dynamic Method Invocation without Reflection - c#

Does anyone knows how can I invoke method dynamically without reflection?
I`ll try to specify my question below
Suppose we have an interface IMyInterface and MyImplementation is an implementation of IMyInterface. Besides of that I have a generic proxy class MyProxy<T> where T : IMyInterface. In this proxy I wanna wrap all calls to all methods that have been defined in MyImplementation and in all inheritors of this class. The purpose I wanna achieve is the dynamic method invocation. In case of reflection everything will be transparent, but as I understand it might be quite slow. Does anyone know about solution that could be much faster?
Thanks a lot!
-- update
hmm, looks like my previous descriptions was not good, so I`ll try to describe my question again. With examples :)
So, lets imagine that we have the following code:
public interface IMyInterface
{
void Method();
}
public class MyImplementation : IMyInterface
{
public void Method()
{
Console.WriteLine("Yeaah!");
}
}
The important point that I forgot to mention is that we have a class named for example Holder. This class should be used by the following way
var holder = // the way of instantiation doesn`t really matters
holder.Register(myImplementationInstance);
var myInterfaceInstance = holder.Resolve<IMyInterface>();
myInterfaceInstance.Method();
Holder instance will return some wrapper that will implement IMyInterface and will wrap the real instance of myImplementation that has been registered.
As I said above we have a wrapper MyImplementationWrapper that implements IMyInterface and has the method named Method with the following body
public void Method()
{
_wrappedInstance.Method();
}
So, there are two questions
a) How can I automatically create the wrapper for myImplementationInstance (I dont want to know anything about object that will be registred inHolder)
b) How can I dynamically invoke the methods ofmyImplementationInstance` by its wrapper

First things first. Have you made sure that Reflection is not too slow for your needs? Do not go on hearsay - test it yourself.
Edit: To include the use of dynamic
Secondly if you are in the .net 3.5 or .net 4.0 then you can use Iron Python (or in the case of the 4.0 - any DLR language or dynamic) to do the dynamic invocation.
The DLR is a very optimal solution for this kind of thing. In C# you can use the dynamic keyword to access the dlr

I'm not sure what you're trying to achieve. It sounds, though, that what you want is a decorator, which does not require reflection.

This seems like you're trying to re-implement polymorphism...
class MyBaseImplementation
{
public virtual void MyMethod()
{
Console.WriteLine("Base");
}
}
class MyDerivedImplementation : MyBaseImplementation
{
public override void MyMethod()
{
Console.WriteLine("Derived");
}
}
static void DoSomething(MyBaseImplementation instance)
{
instance.MyMethod();
}
static void Main(string[] args)
{
MyBaseImplementation inst = new MyDerivedImplementation();
DoSomething(inst);
}
This will print "Derived", even though the parameter in the function is of type "MyBaseImplementation"

Related

Not sure how to properly do this

Ok, so working on a dotnet Core 2 console app that I'm designing to run either on Windows or *Nix. Now the the part I'm trying to figure out is I want to only have one code base and let the code determine if it's running on Win then go one path, or if on *Nix go another path.
So what I'm thinking is create an Interface with the way I want the classes for the two paths to look as far as properties and methods, then create a Win and Nix class implementing the interface.
Seems straightforward, but what I am racking my brain on is how exactly do I create the object based on the OS? I have wrapper code for "IsWindows" and "IsNix" that returns a boolean each, so my thought is to use a If statement to do this. Not sure how to create a generic global variable, then instantiate it in the conditional statement.
Maybe I'm off my rocker and trying to do something odd here, if I am I'm not afraid to be told that. My only other thought is to perform the work inside the conditional statement, but that really would negate my desire to create the object in the conditional based on the OS, then call the same code going forward, using the classes that implement the Interface to make the different code calls as appropriate.
So I feel like a complete idiot with brain lock. Simply creating an object of the type of the Interface is all I needed to do, then set it to an instance of the class in the conditional statement. Easy peasy, not sure why I had a brain fart on that one.
Having common interface and two classes implementing it for different OS'es is definitelly good approach. So let's assume you have
public interface IMyInterface
{
void DoSomething();
}
public class WinClass: IMyInterface
{
public void DoSomething()
{
//Implementation of DoSomething for Windows
}
}
public class NixClass : IMyInterface
{
public void DoSomething()
{
//Implementation of DoSomething for *nix
}
}
Common way to instantiate different implementations of interface (or abstract class) based on certain conditions is using Factory pattern. This might look like this:
public static class MyInterfaceFactory
{
public static IMyInterface CreateMyInterface()
{
if (IsWindows)
return new WinClass();
else if (IsNix)
return new NixClass();
else
throw new PlatformNotSupportedException();
}
}
This is the only platform-dependent part of your code, rest of your code will use only IMyInterface and will be platform independent. You can either use this factory whenever you need to create new instance implementing IMyInterface, or you can use Singleton pattern to ensure, that only one objects will be created for entire application:
public static class MyInterfaceSingleton
{
static MyInterfaceSingleton()
{
Instance = MyInterfaceFactory.CreateMyInterface();
}
public static IMyInterface Instance { get; private set; }
// In C# 7, you can use just this instead:
// public static IMyInterface Instance { get; } = MyInterfaceFactory.CreateMyInterface();
}
Your application then simply call MyInterfaceSingleton.Instance.DoSomething(); whenever needed, in a platform independent way.

Using a public method of derived class that is not in interface definition

New to OOP here. I have defined an interface with one method, and in my derived class I defined another public method. My client code is conditionally instantiating a class of the interface type, and of course the compiler doesn't know about the method in one of the derived classes as it is not part of the underlying interface definition. Here is what I am talking about:
public interface IFileLoader
{
public bool Load();
}
public class FileLoaderA : IFileLoader
{
public bool Load();
//implementation
public void SetStatus(FileLoadStatus status)
{
//implementation
}
}
public class FileLoaderB : IFileLoader
{
public bool Load();
//implementation
//note B does not have a SetStatus method
}
public enum FileLoadStatus
{
Started,
Done,
Error
}
// client code
IFileLoader loader;
if (Config.UseMethodA)
{
loader = new FileLoaderA();
}
else
{
loader = new FileLoaderB();
}
//does not know about this method
loader.SetStatus (FileStatus.Done);
I guess I have two questions:
What should I be doing to find out if the object created at run-time has the method I am trying to use? Or is my approach wrong?
I know people talk of IOC/DI all the time. Being new OOP, what is the advantage of using an IOC in order to say, "when my app asks
for an IFileLoader type, use concrete class x", as opposed to simply
using an App.Config file to get the setting?
Referring to your two questions and your other post I'd recommend the following:
What should I be doing to find out if the object created at run-time has the method I am trying to use? Or is my approach wrong?
You don't necessarily need to find out the concrete implementation at runtime in your client code. Following this approach you kinda foil the crucial purpose of an interface. Hence it's rather useful to just naïvely use the interface and let the concrete logic behind decide what's to do.
So in your case, if one implementation's just able to load a file - fine. If your other implementation is able to the same and a bit more, that's fine, too. But the client code (in your case your console application) shouldn't care about it and just use Load().
Maybe some code says more than thousand words:
public class ThirdPartyLoader : IFileLoader
{
public bool Load(string fileName)
{
// simply acts as a wrapper around your 3rd party tool
}
}
public class SmartLoader : IFileLoader
{
private readonly ICanSetStatus _statusSetter;
public SmartLoader(ICanSetStatus statusSetter)
{
_statusSetter = statusSetter;
}
public bool Load(string fileName)
{
_statusSetter.SetStatus(FileStatus.Started);
// do whatever's necessary to load the file ;)
_statusSetter.SetStatus(FileStatus.Done);
}
}
Note that the SmartLoader does a bit more. But as a matter of separation of concerns its purpose is the loading part. The setting of a status is another class' task:
public interface ICanSetStatus
{
void SetStatus(FileStatus fileStatus);
// maybe add a second parameter with information about the file, so that an
// implementation of this interface knows everything that's needed
}
public class StatusSetter : ICanSetStatus
{
public void SetStatus(FileStatus fileStatus)
{
// do whatever's necessary...
}
}
Finally your client code could look something like the follwing:
static void Main(string[] args)
{
bool useThirdPartyLoader = GetInfoFromConfig();
IFileLoader loader = FileLoaderFactory.Create(useThirdPartyLoader);
var files = GetFilesFromSomewhere();
ProcessFiles(loader, files);
}
public static class FileLoaderFactory
{
public static IFileLoader Create(bool useThirdPartyLoader)
{
if (useThirdPartyLoader)
{
return new ThirdPartyLoader();
}
return new SmartLoader(new StatusSetter());
}
}
Note that this is just one possible way to do what you're looking for without having the necessity to determine IFileLoader's concrete implementation at runtime. There maybe other more elegant ways, which furthermore leads me to your next question.
I know people talk of IOC/DI all the time. Being new OOP, what is the advantage of using an IOC [...], as opposed to simply using an App.Config file to get the setting?
First of all separating of classes' responsibility is always a good idea especially if you want to painlessly unittest your classes. Interfaces are your friends in these moments as you can easily substitute or "mock" instances by e.g. utilizing NSubstitute. Moreover, small classes are generally more easily maintainable.
The attempt above already relies on some sort of inversion of control. The main-method knows barely anything about how to instantiate a Loader (although the factory could do the config lookup as well. Then main wouldn't know anything, it would just use the instance).
Broadly speaking: Instead of writing the boilerplate factory instantiation code, you could use a DI-Framework like Ninject or maybe Castle Windsor which enables you to put the binding logic into configuration files which might best fit your needs.
To make a long story short: You could simply use a boolean appSetting in your app.config that tells your code which implementation to use. But you could use a DI-Framework instead and make use of its features to easily instantiate other classes as well. It may be a bit oversized for this case, but it's definitely worth a look!
Use something like:
if((loader as FileLoaderA) != null)
{
((FileLoaderA)loader).SetStatus(FileStatus.Done);
}
else
{
// Do something with it as FileLoaderB type
}
IoC is normally used in situations where your class depends on another class that needs to be setup first, the IoC container can instantiate/setup an instance of that class for your class to use and inject it into your class usually via the constructor. It then hands you an instance of your class that is setup and ready to go.
EDIT:
I was just trying to keep the code concise and easy to follow. I agree that this is not the most efficient form for this code (it actually performs the cast twice).
For the purpose of determining if a particular cast is valid Microsoft suggests using the following form:
var loaderA = loader as FileLoaderA;
if(loaderA != null)
{
loaderA.SetStatus(FileStatus.Done);
// Do any remaining FileLoaderA stuff
return;
}
var loaderB = loader as FileLoaderB
if(loaderB != null)
{
// Do FileLoaderB stuff
return;
}
I do not agree with using is in the if. The is keyword was designed to determine if an object was instantiated from a class that implements a particular interface, rather than if a cast is viable. I have found it does not always return the expected result (especially if a class implements multiple interfaces through direct implementation or inheritance of a base class).

Why C# don't accept constructor requirements with parameters on generics?

Working with C# Generics you can have a class like this:
class Foo<T> where T:new() {}
Which means that the type T should have a constructor without parameters. It would be nice if we could have:
class Foo<T> where T : new(string)
{
private T CreateItem()
{
string s="";
return new T(s);
}
}
Is there any reason that Microsoft haven't added this feature to the language?
Is there any reason that Microsoft haven't added this feature to the language?
The feature you describe is a specific case of the of the more general feature "allow a constraint that requires a particular method to exist". For example, you might say:
void M<T>(T t) where T has an accessible method with signature double Foo(int)
{
double x = t.Foo(123);
}
We don't have that feature in C# because features have to be justified by a cost-benefit analysis. That would be a pretty expensive feature from both a design and implementation point of view -- a feature that would drive requirements onto not just C# but every .NET language. What's the compelling benefit that justifies the feature?
Moreover: suppose we did design that feature. How would it be implemented efficiently? The constraints in the generic type system have been carefully designed so that the jitter can generate efficient code once that can then be shared for every reference type. How would we generate efficient code for arbitrary method pattern matching? That sort of efficient dispatch is pretty straightforward when the method's slot can be known at compile time; with this feature we would no longer have that advantage.
The feature you want is the same feature, just with the kind of method restricted to a constructor.
Remember, the purpose of generics is to let you write generically typed code. If you're requiring constraints that are more specific than things that can be captured in the type system then you might be trying to abuse generics.
Rather than try to guess why Microsoft decided on a particular implementation, here's a workaround for you, using the factory pattern
public interface IFactory<T>
{
T CreateItem(string s);
}
class Foo<TFactory,T> where TFactory : IFactory<T>, new()
{
private T CreateItem()
{
var factory = new TFactory();
string s="";
return factory.CreateItem(s);
}
}
Using this pattern, say you have a class Bar which has a constructor taking a single string:
public class Bar
{
public Bar(string laa)
{}
}
You just need a BarFactory which implements IFactory<Bar>
public class BarFactory : IFactory<Bar>
{
public BarFactory () {}
public Bar CreateItem(string s)
{
return new Bar(s);
}
}
Now you can use that factory with Foo
var foo = new Foo<BarFactory,Bar>(); // calls to CreateItem() will construct a Bar
The solution I adopted when I wanted a generic function that invoked a constructor with arguments was to use reflection to find and invoke it.
Given that I had control of both the generic, and all the classes it was implemented over (and this function was the only place those classes were constructed), I think I might have been better to give the classes a default constructor and added an Initialize method in the interface they all implemented.
(A solution that allowed adding static methods in general to an interface would be ideal.)

One method shared by several classes

I have just one method that I need several different classes to access and it just seems lame to make a utility class for just one method. The classes that need to use this method are already inheriting an abstract class so I can't use inheritance. What would you guys do in this situation?
[I]t just seems lame to make a utility
class for just one method
Just do it, it will grow. It always does. Common.Utilities or something of that nature is always necessary in any non-trivial solution.
Keep in mind that a class is just a small, focused machine. If the class only has one method then it's just a very small, focused machine. There's nothing wrong with it, and centralizing the code is valuable.
There is a cheat that you can use :-)
Create an Interface that your classes can "implement" but, create an extension method on that interface, your classes then magically get that method without having to call the utility class...
public Interface IDoThisThing {}
public static void DoThisThingImpl(this IDoThisThing dtt)
{
//The Impl of Do this thing....
}
Now on your classes you can just add the IDoThisThing
public class MyClass, MyBaseClass, IDoThisThing
{
//...
}
and they Get that thing :-)
Note, this is only syntatic sugar around effectively a utility class, but it does make the client code very clean (as just appears as a method on your class).
What do you mean you can't use inheritance?
If you write the method in the abstract class, you can also write the implementation (not everything in an abstract class needs to be abstract).
But generally, it's advisable to have some sort of 'GeneralUtils' class; cause you end up with a few of these functions.
I'd need more info to give a definite answer.
However a well-named class with a single well-named method could work wonders for readability (as compared to an inheritance based solution for instance)
Since you use the term utility method, I'd say create a static class with the static method and be done with it.
can use extension methods...
namespace ExtendMe
{
public interface IDecorate { }
public static class Extensions
{
public static void CommonMethod(this IDecorate o) { /* do stuff */ }
}
public class Blah :IDecorate {}
public class Widget : IDecorate {}
class Program
{
static void Main(string[] args)
{
new Blah().CommonMethod();
new Widget().CommonMethod();
}
}
}

Modify C# Class method during execution

I'd like to override a class method without inheriting the base class because it'd take a lot of time and modifications and, therefore, more and more tests. It's like this:
class TestClass{
public void initialMethod(){
...
}
}
And somewhere on the code, I'd like to do something like this:
public testMethod()
{
return;
}
test(){
changeMethod(TestClass.initialMethod, testMethod);
}
And this changeMethod function would override the TestClass initialMethod so that it'd call testMethod instead.
Inheriting and overriding the method using normal practices is not an option, as this class A is a graphic component and, inhereting it (and changing it) would break lots of code.
Edit: We don't have the base code for the TestClass, so it's not an option to modify the code there defining the initialMethod as a delegate.
Edit 2: Since this is a graphical component, the designer added a lot of code automatically. If I were to inherit this code, I would have to replace all code added by the designer. That's why I wouldn't like to replace this component.
You need the Strategy pattern.
Main steps:
Create an interface with ie. Do() signature
Your initialMethod() should call a strategy.Do(), where strategy is type of your interface
Create a class that implements this interface. Do() is your testmethod now.
Inject into your main class an instance of this class
If the job it's not so big (let's say just a color replacement or something) then I agree with Jhonny D. Cano's solution with C# (anonymous)delegates.
Edit (after edit 2)
May - just as proof-of-concept - you should inherit the class and replace all references from base class to this new. Do this, and nothing else. If it works, you can think about the next steps (new methods or delegates etc.)
You need only a new checkout from your version control system, and if it maybe fails you can abandon it. It's worth trying.
Perhaps you can do it as a delegate.
class TestClass {
public Action myAction;
public void initialMethod(){
...
}
initialMethod
public TestClass() {
myAction = initialMethod;
}
}
and then on TestMethod
public testMethod()
{
return;
}
test() {
testClassInstance.myAction = testMethod;
}
I think your best bet might be to use a AOP framework like LinFu. There's a codeproject article explaining it:
Introducing LinFu, Part VI: LinFu.AOP – Pervasive Method Interception and Replacement for Sealed Types in Any .NET Language
If 'TestClass' is something you defined, you could replace the 'initialMethod' definition with a property and delegate which can then be set to any method with a given signature. (Even anonymous ones.)
class TestClass {
Action _myMethod;
Action MyMethod {
get { return _myMethod; }
set { _myMethod = value; }
}
var tc = new TestClass()
tc.MyMethod = () -> Console.WriteLine("Hello World!");
tc.MyMethod()
The above code is untested.
The short and simple answer is: if you can't adjust the base TestClass code, no, there's no way you can modify the class to replace a method by another. Once we started doing stuff like that, we'd be in a completely different kind of language, like JavaScript.
The longer answer is: it depends on who is calling the replaced method.
If it's other classes, see if you can't implement a Proxy in between them and the unmodifiable concrete class. Whether this is doable depends on whether that class implements interfaces, or is its own interface.
If it's the class itself, then your only option is to decompile and modify the class, at design time using Reflector (or equivalent tools), or at runtime using Reflection.Emit. However, you'd have to be hurting pretty badly to go this route, as it's sure to be painful and brittle.
Unfortunately you still haven't explained what you are trying do and why. Replacing methods on the go is powerful stuff in the languages that permit it directly... There might be mocking libraries that can be twisted sufficiently far to do the reflection stuff, but then you'd be skating on thin ice.
If you don't have the code use Extension Methods.
public void doSmth(this objectYOUWANT arg)
{
//Do Something
}
Here you use the principle Closed for Modification Open for Extension.
This will add functionality to the library you don't have the source code. It's very clean to do it this way.
Edition:
In FrameWork 3.5 there is something new called Extension Methods. These kind of methods adds functionality to a closed Assembly letting you Extend in functionality a closed dll/assembly.
To use this for example you have a dll that you import, that is called Graphics.dll (you have the reference on your project)
First of all you shoud create a new static class called for example Extension:
public static class Extensions
{
}
Second, you want to add extra functionality to a class contained in Graphics.dll named ChartGraph. You will do this:
public static class Extensions
{
public static void draw(this ChartGraph g)
{
// DO SOMETHING
}
}
Third, when you instantiate a new object from the graphics.dll you now will have the new method you have created:
ChartGraph myG = new ChartGraph();
myG.draw();
As you can see there you have added new functionality without much effort without recompiling the dll, this is good if you don't have the source code.

Categories