C # code listing all methods invoked by the launch method?

Say we have a method A () that calls method B () and methodC ().

In method B (), we call method B1 () and methodB2 ().

In the C () method, we call methodC1 (), methodC2 (), and methodC3 ().

So at the end we have a tree of methods

Methoda

methodB

methodB1

methodB2

methodC

methodC1

methodC2

methodC3

Is it possible to have this list through C # code?

+6
source share
2 answers

The first thing that comes to our mind when we think about defining a call flow is to check the call stack. But checking the stack frames can only give us the current call hierarchy, not the previous one. ie Even if you check the stack frames in C3, it will not have call history A B. This does not work.

This means that each method invoked must also somehow participate in achieving this goal. Each method must somehow determine that the caller wants to track the flow and should help provide the necessary information. But adding some code to every possible method that you can name is just ridiculous.

Another way to do this is to delegate this to someone who can intercept every method call, check if the caller wants to monitor the flow, and register the required information, which can be accessed later. It is here that I think Aspect Oriented Programming (AOP) is included in the image. To use AOP in .Net, check out PostSharp. If I get the time, I will try to come up with a sample code, but for now I can only point to this URL: http://www.postsharp.net

Hope this helps.

+2
source

If you can implement each specific operation as a separate class (which I recommend), this will be next. If not, you should use AOP . I would recommend Dynamic Proxy Lock for AOP.

class Program { static void Main(string[] args) { new A().Invoke(); CallStack.Get().ToList().ForEach(Console.WriteLine); Console.ReadKey(); } } public class CallStack { private CallStack() { _callStack = new Stack<string>(); } private static CallStack _singleton; private Stack<string> _callStack; public static CallStack Get() { if (_singleton == null) _singleton = new CallStack(); return _singleton; } public static void Push(string call) { Get()._callStack.Push(call); } public List<string> ToList() { return new List<string>(_callStack); } } public abstract class MethodBase { protected void Trace() { CallStack.Push(GetType().Name); } protected abstract void Operation(); public void Invoke() { Trace(); Operation(); } } public class A : MethodBase { protected override void Operation() { new B().Invoke(); new C().Invoke(); } } public class B : MethodBase { protected override void Operation() { new B1().Invoke(); new B2().Invoke(); } } public class C : MethodBase { protected override void Operation() { new C1().Invoke(); new C2().Invoke(); new C3().Invoke(); } } public class B1 : MethodBase { protected override void Operation() { } } public class B2 : MethodBase { protected override void Operation() { } } public class C1 : MethodBase { protected override void Operation() { } } public class C2 : MethodBase { protected override void Operation() { } } public class C3 : MethodBase { protected override void Operation(){} } 
+1
source

Source: https://habr.com/ru/post/957809/


All Articles