This question already has answers here:
Retrieving the calling method name from within a method [duplicate]
(7 answers)
Closed 4 years ago.
I am implementing simple logging, and I would like to do something like below
public int SomeMethod(int x)
{
Log(SomeMethod,"here is a log entry);
}
In the Log method, I would like to parse out the class name from the method and print to the log file the method name and class name.
Is it possible to do something that would look as simple as above or something similar?
you could use nameof if you are using C# 6 or later
public int SomeMethod(int x)
{
Log(nameof(SomeMethod), "here is a log entry");
}
Try this with Reflection
var currentMethodName = System.Reflection.MethodBase.GetCurrentMethod().Name;
var currentCalssName = System.Reflection.MethodBase.GetCurrentMethod().DeclaringType.Name;
Or you can implement your Log method like these
public static void Log<TCallerClass>(string text, [CallerMemberName]string method = "")
{
var callerMethodName = method;
var callerCalssName = typeof(TCallerClass).FullName;
}
Usage : Log<YourClass>("here is a log entry");
public static void Log(string text)
{
var stackFrame = new StackFrame(1, true);
var callerMethodName = stackFrame.GetMethod().Name;
var callerCalssName = stackFrame.GetMethod().DeclaringType.Name;
}
Usage : Log("here is a log entry");
This question already has answers here:
Why Doesn't C# Allow Static Methods to Implement an Interface?
(28 answers)
Closed 6 years ago.
I have the following interface
public interface IQueryBuilder
{
SqlCommand Build(IReportDataSource dataSource, List<IReportColumn> columns, List<IReportRelationMapping> relationMappings, IReportFilterMapping filters, List<IReportColumn> columsToSortBy, ReportFormat reportFormat);
string GetSqlClause(List<IReportFilter> reportFilters, ref List<IDataParameter> sqlParams);
}
However, I would like to be able to access the method GetSqlClause in the implementation directly.
Here is how I implemented the above
public class QueryBuilder : IQueryBuilder
{
public SqlCommand Build(IReportDataSource dataSource, List<IReportColumn> columns, List<IReportRelationMapping> relationMappings, IReportFilterMapping filters, List<IReportColumn> columsToSortBy, ReportFormat reportType)
{
//Do something awsome!!!
string sqlQuery = "";
List<IDataParameter> sqlParameters = new List<IDataParameter>();
return this.GetSqlCommand(sqlQuery, sqlParameters);
}
private SqlCommand GetSqlCommand(string sqlQuery, List<IDataParameter> sqlParams)
{
var command = new SqlCommand(sqlQuery);
foreach (IDataParameter dataParameter in sqlParams)
{
command.Parameters.Add(dataParameter);
}
return command;
}
public static string GetSqlClause(List<IReportFilter> reportFilters, ref List<IDataParameter> sqlParams)
{
string sqlFilter = "";
if (reportFilters != null && reportFilters.Any())
{
//At this point we know there are some filter to add to the list
var firstFilter = reportFilters.First();
foreach (var reportFilter in reportFilters)
{
var parameter = GenerateDbParameter("p" + sqlParams.Count, reportFilter.FormattedValue, SqlDbType.NVarChar);
....
....
}
}
return sqlFilter;
}
private static IDataParameter GenerateDbParameter(string parameterName, object parameterValue, SqlDbType parameterType)
{
if (string.IsNullOrEmpty(parameterName) || parameterValue == null)
{
throw new ArgumentException();
}
var parameter = new SqlParameter("#" + parameterName, parameterType)
{
Value = parameterValue
};
return parameter;
}
}
Because I am using static on my GetSqlClause method I get an error
cannot implement an interface member because it is static.
What is a good work around to this problem? How can I access my GetSqlClause directly?
If you want your method to be static and implement an interface, the language won't let you do that, but you can work around it in several ways:
If accessing the whole implementation from a static context makes sense, you can simply declare a singleton object:
public static QueryBuilder Instance { get; } = new QueryBuilder();
And now you have access to the QueryBuilder.Instance static property, whose value implements IQueryBuilder.
Through an explicit method implementation. This is an additional instance method which implements the interface method, and whose signature won't conflict with another method in the class.
string IQueryBuilder.GetSqlClause(List<IReportFilter> reportFilters, ref List<IDataParameter> sqlParams)
{
// Call the static method, this is *not* a recursive call
return GetSqlClause(reportFilters, ref sqlParams);
}
The general syntax of an explicit implementation is:
ReturnType InterfaceName.MethodName(ParamType param)
{
...
}
Another (simpler) solution would be to use two distinct method names.
C# doesn't support static members implementing interface methods.
I am trying to construct some objects in a reasonably generic way. Some of the objects have constructor params, others don't.
What I am trying to achieve is to return some kind of builder function to which I can supply the constructor param if required.
I know I could have optional params passed down, but in my real scenario, there are several layers and I'm loathed to add optional params down the hierarchy.
I'm not too up on partial application/currying, but could I use that here and if so, how?
Here's a bit of sample code - which won't work - to try and explain a bit more what I'm after.
public void Main()
{
dynamic buildClass = ClassBuilder<BaseClass>(true);
// ideally I'd like to be able to supply the constructor data
// here
var theClass = buildClass(???)
}
public Func<???, TClass> ClassBuilder<TClass>(bool flag) where TClass : BaseClass
{
// obviously this won't work since the delegates have different
// signatures
if (flag) return () => GetClassA();
return (x) => GetClassB(x);
}
public object GetClassA()
{
return new ClassA();
}
public object GetClassB(string param)
{
return new ClassB(param);
}
public class BaseClass {}
public class ClassA : BaseClass {}
public class ClassB : BaseClass
{
private string _param;
public ClassB(string param)
{
_param = param;
}
}
Many thx
S
To elaborate #Sylwekqaz you could have something like below, and not restrict yourself for type of BaseClass.
public static class Builder
{
public static T Build<T>(params object[] args) where T : class
{
var info = typeof(T).GetConstructor(args.Select(arg => arg.GetType()).ToArray());
if (info == null)
throw new ArgumentException(#"Can't get constructor :(", "args");
return (T)info.Invoke(args.ToArray());
}
}
And then you can call your builder as
var a = Builder.Build<ClassA>();
var b = Builder.Build<ClassB>(); // need parameterless ctor in ClassB
var c = Builder.Build<ClassB>("param");
You must use code reflection to detect constructor/method with you parameters and invoke it.
Type type = typeof(YourClass);
ConstructorInfo ctor = type.GetConstructor(new[] { typeof(string) });
object instance = ctor.Invoke(new object[] { 10 });
~source: Using C# reflection to call a constructor
alternatively you have a class MethodInfo if you must use methods GetClassX
More info
https://msdn.microsoft.com/en-us/library/system.type.getconstructor%28v=vs.110%29.aspx
https://msdn.microsoft.com/en-us/library/system.reflection.constructorinfo.invoke%28v=vs.110%29.aspx
I don't entirely follow your code example, but you ask about partial-application and currying...
The best way I've found is to just create N functions that take from 1-N generic parameters, then let the compiler pick the one you want. If you take a look at my language-ext project I have two functions, one called curry and one called par for currying and partial application:
Currying source
Partial application source
To partially apply, do this:
// Example function
int AddFour(int a,int b,int c, int d)
{
return a + b + c + d;
}
// This returns a Func<int,int,int> with the first two arguments 10 & 5 auto-provided
var tenfive = par(AddFour, 10, 5);
// res = 10 + 5 + 1 + 2
var res = tenfive(1,2);
To curry, do this:
// Example function
int AddFour(int a,int b,int c, int d)
{
return a + b + c + d;
}
// Returns Func<int,Func<int,Func<int,Func<int,int>>>>
var f = curry(AddFour);
// res = 10 + 5 + 1 + 2
var res = f(10)(5)(1)(2);
This question already has answers here:
get methodinfo from a method reference C#
(7 answers)
Closed 9 years ago.
Is it possible to get a MethodInfo object from a method symbol?
So in the same vein as:
typeof(SomeClassSymbol) // this gets you a Type object
Here is what I want to do:
public class Meatwad
{
MethodInfo method;
public Meatwad()
{
method = ReflectionThingy.GetMethodInfo(SomeMethod);
}
public void SomeMethod() { }
}
How could I implement ReflectionThingy.GetMethodInfo? Given this is even possible at all, what about overloaded methods?
Delegates contain the MethodInfo you want in their Method property. So your helper method could be as simple as:
MethodInfo GetMethodInfo(Delegate d)
{
return d.Method;
}
You cannot convert directly from a method group to Delegate. But you can use a cast for that. E.g.:
GetMethodInfo((Action)Console.WriteLine)
Be aware that this won't work if you try to mix it with something like usr's solution. For example
GetMethodInfo((Action)(() => Console.WriteLine()))
will return the MethodInfo for the generated anonymous method, not for Console.WriteLine().
This is not possible in C# directly. But you can build this yourself:
static MemberInfo MemberInfoCore(Expression body, ParameterExpression param)
{
if (body.NodeType == ExpressionType.MemberAccess)
{
var bodyMemberAccess = (MemberExpression)body;
return bodyMemberAccess.Member;
}
else if (body.NodeType == ExpressionType.Call)
{
var bodyMemberAccess = (MethodCallExpression)body;
return bodyMemberAccess.Method;
}
else throw new NotSupportedException();
}
public static MemberInfo MemberInfo<T1>(Expression<Func<T1>> memberSelectionExpression)
{
if (memberSelectionExpression == null) throw new ArgumentNullException("memberSelectionExpression");
return MemberInfoCore(memberSelectionExpression.Body, null/*param*/);
}
And use it like this:
var methName = MemberInfo(() => SomeMethod()).MethodName;
That will provide you compile-time safety. Performance will not be good though.
Is there any way to do something like this in C#?
public void DoSomething(string parameterA, int parameterB)
{
}
var parameters = ("someValue", 5);
DoSomething(parameters);
Close, but unfortuantely only using object (so you get lots of boxing/unboxing)
public void DoSomething(params object[] parameters)
{
}
var parameters = new object[]{"someValue", 5};
DoSomething(parameters); // this way works
DoSomething("someValue", 5); // so does this way
Not today, no. We are at present prototyping exactly that feature for a possible hypothetical future version of C#.
If you can provide a really awesome reason why you want this feature, that would be points towards actually getting it out of prototyping and into a possible hypothetical future release. What's your awesome scenario that motivates this feature?
(Remember, Eric's speculations about possible hypothetical future releases of C# are for entertainment purposes only and are not to be construed as promises that there ever will be such a release or that it will have any particular feature set.)
No need to use reflection if you first store as a delegate, but it does require a strong declaration of the delegate.
public void DoSomething(string parameterA, int parameterB)
{
Console.WriteLine(parameterA+" : "+parameterB);
}
void Main()
{
var parameters = new object[]{"someValue", 5};
Action<string,int> func=DoSomething;
func.DynamicInvoke(parameters);
}
...and you can forget about compile-time type/sanity checking of the parameter list. Probably a bad thing.
You can invoke it through reflection, but that'll incur some overhead:
using System;
using System.Reflection;
namespace SO2744885
{
class Program
{
public void DoSomething(string parameterA, int parameterB)
{
Console.Out.WriteLine(parameterA + ": " + parameterB);
}
static void Main(string[] args)
{
var parameters = new object[] { "someValue", 5 };
Program p = new Program();
MethodInfo mi = typeof(Program).GetMethod("DoSomething");
mi.Invoke(p, parameters);
}
}
}
Of course, if you can change the method signature to take an array, that'll work as well, but that will look worse in my opinion.
nope - this is not possible.
Maybe this way is more "clean":
// standard method calling
DoSomething( "Johny", 5 );
// since C# 4.0 you can used "named parameters"
DoSomething( name: "Johny", number: 5 );
// calling with parameter's "container"
DoSomething( new DoSomethingParameters( "Johny", 5 ) );
// calling with parameter's "container"
DoSomething( new DoSomethingParameters{ Name = "Johny", Number = 5 } );
// calling with callback for parameters initialization
DoSomething( p => { p.Name = "Johny"; p.Number = 5; } );
// overload of DoSomething method with callback, which initialize parameters
public void DoSomething( Action<DoSomethingParameters> init ) {
var p = new DoSomethingParameters();
init( p );
DoSomething( p );
}
// overload of DoSomething method for calling with simple parameters
public void DoSomething( string name, int number ) {
var p = new DoSomethingParameters( name, number );
DoSomething( p );
}
// the "main executive" method which is "doing the work"
// all posible parameters are specified as members of DoSomethingParameters object
public void DoSomething( DoSomethingParameters p ) { /* ... */ }
// specify all parameters for DoSomething method
public class DoSomethingParameters {
public string Name;
public int Number;
public DoSomethingParameters() { }
public DoSomethingParameters( string name, int number ) {
this.Name = name;
this.Number = number;
}
}
Inspired by Steven's answer:
static public void Execute<T1, T2>(this Tuple<T1, T2> parameters, Action<T1, T2> action)
{
action(parameters.Item1, parameters.Item2);
}
var parameters = Tuple.Create("someValue", 5);
parameters.Execute(DoSomething);
I like Henrik's answer, except that it imposes a somewhat weird syntax: parameters call a method on themselves. I would do it the other way around. Only problem with this approach is that it makes you explicitly cast a method to a delegate.
Anyway, here's the basic idea:
// wrapped code to prevent horizontal overflow
public static void Execute<T1, T2>
(this Action<T1, T2> action, Tuple<T1, T2> parameters) {
action(parameters.Item1, parameters.Item2);
}
And so on (for more Ts).
Usage:
var parameters = Tuple.Create("Hi", 10);
Action<string, int> action = DoSomething;
action.Execute(parameters);
You can also easily do this with a return value:
// wrapped code to prevent horizontal overflow
public static TResult Return<T1, T2, TResult>
(this Func<T1, T2, TResult> func, Tuple<T1, T2> parameters) {
return func(parameters.Item1, parameters.Item2);
}
And so on.
I'd also like to point out that just because you aren't on .NET 4.0, that doesn't mean you can't easily implement your own Tuple<T1, T2, ...> type.
you can do:
public void DoSomething(string parameterA, int parameterB)
{
}
var func = (Action)(() => DoSomething("someValue", 5));
func();
You can do this (.NET 4.0):
var parameters = Tuple.Create("someValue", 5);
DoSomething(parameters.Item1, parameter.Item2);
If they're all the same type, yes, you can do something to this effect:
public void Print(params string[] args) {
foreach (string arg in args) {
Console.WriteLine(arg);
}
}
// ...
Print("apple", "banana");
Print("apple", "banana", "cherry");
Print("apple", "banana", "cherry", "doughnut");
Otherwise, no, you can't expand parameters in place like that without using reflection. C# doesn't have the equivalent of Ruby's splat operator.
If you don't want to change the method signature why not declare a new method with the appropriate signature and use that as a proxy. Like
public void DoSomething(string parameterA, int parameterB)
{
// Original do Something
}
public void DoSomething(object[] parameters)
{
// some contract check whether the parameters array has actually a good signature
DoSomething(parameters[0] as string,(parameters[1] as int?).Value);
}
var parameters = new object[]{"someValue", 5};
DoSomething(parameters);
You can also try out some of the stuff LinFu.Reflection provides, like Late Binding. With it you can do something like this:
var dosomethingobject = new ObjectThatHasTheDoSomething();
DynamicObject dynamic = new DynamicObject(dosomethingobject);
var parameters = new object[]{"someValue", 5};
dynamic.Methods["DoSomething"](parameters);
For this you need that the DoSomething method is inside an object.
"var" just represents a particular type, it's effectively shorthand for writing a type name. In the above you're not specifying any type. The only way to do this is to make a parameter class to represent the inputs in bulk...
public void DoSomething(Parameters param)
{
...
}
var param = new Parameters("someValue", 5);
DoSomething(param);
...but this is only going to be useful in specific circumstances. You could make multiple Parameters constructors to represent different arrangements of parameters, but the function you're calling will only take ONE input - the Parameters object. So with this you're really undermining the ability to overload a function.
So, in short, no. =)
How about this in .NET 4 (for the sake of curiosity)
public void DoSomething(string parameterA, int parameterB)
{
}
public void Helper(dynamic parameter)
{
DoSomething(parameter.Parameter1, parameter.Parameter2);
}
var parameters = new {Parameter1="lifeUniverseEverything", Parameter2=42};
Helper(parameters);