Reputation: 3
Greetings everyone!
I have a set of a few (and potentially will have dozens more) of very similar methods in C#. They all built on almost identical pattern:
ResultObjectType MethodX(...input parameters of various types...)
{
nesting preparation code here...
{
{
resultObject = ExternalClass.GetResultForMethodX(input parameters of MethodX);
}
}
nesting result processing code here ...
return resultObject;
}
Repeating/identical parts: ResultObjectType, preparation code, result processing code.
Different parts: ExternalClass method to call, input parameter set (number of input parameters, their types).
Important: I am not in control of the method signatures – cannot change them.
I am trying to avoid repeating all blocks of similar code with something like this:
ResultObjectType MethodX(...input parameters of various types...)
{
return UniversalMethod(
new ExternalMethodDelegate(ExternalClass.GetResultForMethodX),
input parameters of MethodX...);
}
ResultObjectType UniversalMethod (Delegate d, input parameters of various types...)
{
nesting preparation code...
{
{
resultObject =
(d as ExternalMethodDelegate)(same input parameters as above);
}
}
nesting result processing code...
return resultObject;
}
So far I only managed to make it work in this manner in case where all parameters have the same known type at the time of coding. After a number of attempts to tackle this problem with generic delegates I am starting to think this is not possible to achieve. Even when my code compiles, it does not work at runtime. Any takers? Thanks in advance for your help!
Upvotes: 0
Views: 1875
Reputation: 35219
Repeating/identical parts: ResultObjectType, preparation code, result processing code.
You should concentrate to make this parts as isolated as possible.
Another approach is code generation.
Upvotes: 0
Reputation: 30580
Here's an example using generic delegates:
int MethodY(int something, int other)
{
return UniversalMethod(() => GetResultForMethodY(something, other));
}
string MethodX(string something)
{
return UniversalMethod(() => GetResultForMethodX(something));
}
T UniversalMethod<T>(Func<T> fetcher)
{
T resultObject;
//nesting preparation code here...
{
resultObject = fetcher();
}
//nesting result processing code here ...
return resultObject;
}
If ResultObjectType is always the same then you can remove all T
s.
Upvotes: 2