23

I am looking for an algorithm that can get the object that called the method, within that method.

For instance:

public class Class1 {

    public void Method () {
        //the question
        object a = ...;//the object that called the method (in this case object1)
        //other instructions
    }

}

public class Class2 {

    public Class2 () {
        Class1 myClass1 = new Class1();
        myClass1.Method();
    }

    public static void Main () {
        Class2 object1 = new Class2();
        //...
    }

}

Is there any way to do this?

Willem Van Onsem
  • 443,496
  • 30
  • 428
  • 555
  • 7
    I have a question, what are you going to do with it once you have it? If you need to get a reference to the calling object then why not just pass it in as a parameter? – Lazarus Feb 10 '10 at 14:18
  • Dupe? http://stackoverflow.com/questions/420541/is-there-any-way-to-get-a-reference-to-the-calling-object-in-c – CraigTP Feb 10 '10 at 14:21
  • 1
    I'm curious: What's the use case? Why do you think you need to do this? – T.J. Crowder Feb 10 '10 at 14:26
  • "I need to have an algorithm that can get the object [that called] a method within the method[.]" Why? What would you use this for? If you elaborate on what you need this for we might be in a better spot to help you solve your problem. – jason Feb 10 '10 at 14:28
  • 1
    (This is a classic case of, "It looks like you're asking the wrong question. Back up a couple steps, because you seem to have gone down the wrong path a while back.") – Greg D Feb 10 '10 at 14:41
  • 1
    Although this question was asked 3 years ago, I just ran into a situation where it would in fact be the best solution. I have an event class, and GUI elements process instances of said events. There's a LOT of code of GUI elements, but one short event class, which can be either used or not. And for debug purposes, it would be great for me to get the exact _instance_ which did use this event (called property setter). Basically, I want to implement debugger functionality, but in a much more convenient way, inside the running code. – Max Yankov Oct 29 '13 at 16:09

4 Answers4

16

Here's an example of how to do this...

...
using System.Diagnostics;
...

public class MyClass
{
/*...*/
    //default level of two, will be 2 levels up from the GetCaller function.
    private static string GetCaller(int level = 2)
    {
        var m = new StackTrace().GetFrame(level).GetMethod();

        // .Name is the name only, .FullName includes the namespace
        var className = m.DeclaringType.FullName;

        //the method/function name you are looking for.
        var methodName = m.Name;

        //returns a composite of the namespace, class and method name.
        return className + "->" + methodName;
    }

    public void DoSomething() {
        //get the name of the class/method that called me.
        var whoCalledMe = GetCaller();
        //...
    }
/*...*/
}

Posting this, because it took me a while to find what I was looking for myself. I'm using it in some static logger methods...

Tracker1
  • 19,103
  • 12
  • 80
  • 106
  • 5
    I should note, that this won't work for your need, as you want the instance of the given object... in which case you should re-think. – Tracker1 Dec 01 '11 at 22:37
  • 7
    Run this in release mode and the compiler will optimize the callstack, which will cause you problems. In .NET 4.5 there's now the `CallerMemberName` attribute – Jon Barker Mar 27 '14 at 18:17
  • 7
    That's it! I really disapprove comments like @Lazarus made ('Why do you even need this') and even more that they are getting upvoted. I needed this for exactly same thing as you, static logger called by many threads. – Mike Aug 10 '14 at 23:40
  • this answer is really underrated, I was looking for a way to do some simple logging, without using NLog, Log4Net, etc. and I didn't know I could create a StackTrace, this solution helped me out. – Droa Jun 27 '19 at 09:42
2

You could get to the current stack trace in code and walk up one step. http://msdn.microsoft.com/en-us/library/system.diagnostics.stacktrace.aspx

But as was commented below, this will get you the method and class calling you, but not the instance (if there is one, could be a static of course).

Teun D
  • 5,045
  • 1
  • 34
  • 44
-1

or just pass the object as method parameter.

public void Method(object callerObject)
{
..
}

and call the Method:

myClass.Method(this);

regards, Florian

-10

Obviously i don't know the exact details of your situation but this really seems like you need to rethink your structure a bit.

This could easily be done if proper inheritance is structured.

Consider looking into an abstract class and classes that inherit from said abstract class. You might even be able to accomplish the same thing with interfaces.

Brian
  • 4,974
  • 2
  • 28
  • 30