19

Does anyone has a good solution for a C# version of the C++ __FUNCTION__ macro? The compiler does not seem to like it.

Filip Frącz
  • 5,881
  • 11
  • 45
  • 67

6 Answers6

26

Try using this instead.

System.Reflection.MethodBase.GetCurrentMethod().Name

C# doesn't have __LINE__ or __FUNCTION__ macros like C++ but there are equivalents

Eoin Campbell
  • 43,500
  • 17
  • 101
  • 157
  • 6
    As this one is top and accepted, can you/someone add: System.Reflection.MethodBase.GetCurrentMethod().ToString() will yield the params too so its not ambiguous in the face of overloads and that System.Reflection.MethodBase.GetCurrentMethod().DeclaringType.ToString() to give the C name (&namespace) – Ruben Bartelink Dec 18 '08 at 15:46
  • 1
    there is a #line metadata-macro, which is used to give debugging information. The compiler will inject them for you, so be careful using it in normal code! – Iain Ballard Jan 19 '11 at 09:40
9

What I currently use is a function like this:

using System.Diagnostics;

public string __Function() {
    StackTrace stackTrace = new StackTrace();
    return stackTrace.GetFrame(1).GetMethod().Name;
}

When I need __FUNCTION__, I just call the __Function() instead. For example:

Debug.Assert(false, __Function() + ": Unhandled option");

Of course this solution uses reflection too, but it is the best option I can find. Since I only use it for Debugging (not Tracing in release builds) the performance hit is not important.

I guess what I should do is create debug functions and tag them with

[ Conditional("Debug") ]

instead, but I haven't got around to that.

Thanks to Jeff Mastry for his solution to this.

Community
  • 1
  • 1
Mark Booth
  • 7,605
  • 2
  • 68
  • 92
6

Unfortunately there is no equivalent version of that macro in C#. I don't consider the GetCurrentMethodName() solution equivalent to the C++ __FUNCTION__ macro. Namely becase the C++ version is a compile time computation of the name. For C# this is a runtime calculation and incurs a performance hit.

I'm not making any assumtions about the severity of the cost but there is one

JaredPar
  • 733,204
  • 149
  • 1,241
  • 1,454
5

The following should work, although it will be evaluated at runtime instead of during compilation.

System.Reflection.MethodBase.GetCurrentMethod().Name
e.James
  • 116,942
  • 41
  • 177
  • 214
3

I use this:

public static string CallerName([CallerMemberName] string callerName = "")
{
    return callerName;
}

Usage example:

s_log.DebugFormat("{0}", CallerName());

The down side of using it is that every time you want to print the caller name, you need to jump to the function ==> time consuming & performance hit! So, I use it for debugging perpose and if I need to print also in production code, I usually inline the function name into the log.Debug, e.g. :

s_log.Debug("CallerName");

HTH..

ShloEmi
  • 1,851
  • 2
  • 20
  • 25
2

This is added in .NET 4.5.

See @roken's answer here:

Do __LINE__ __FILE__ equivalents exist in C#?

Community
  • 1
  • 1
jm.
  • 23,422
  • 22
  • 79
  • 93