There is a simple console application in which the recursive method is written. In general, it looks like this

namespace somenamespace { class Program { static void Main(string[] args) { Recursive(...) } static void Recursie(...) { } } } 

Accordingly, the method refers to itself and during its operation I need a variable that would save some value associated with this method. Suppose in one branch of the cycle in the method I increase it, in the other I decrease it and use it during the operation of the method. What to do in this case?

Why if I declare this method without static, does the program require an instance? How to make this copy? If through new Program() , then what will happen to the void Main ?

    4 answers 4

    Accordingly, the method refers to itself and during its operation I need a variable that would save some value associated with this method.

    Add a static field and work with it:

     namespace somenamespace { class Program { private static int value = 0; static void Main(string[] args) { Recursive(...) } static void Recursive(...) { value++; } } } 

    Why if I declare this method without static, does the program require an instance? How to make this copy? If through new Program (), then what will happen to the void Main?

    Because from static methods without specifying an instance, only static methods can be called. The reason for this is that the reference methods are implicitly passed to the instance methods of the object instance that calls this method (if the static method is called, there is no this link).

    In the simplest case, you can really do a Recursive instance and create a Program instance. There will be nothing with the Main method.

     namespace somenamespace { class Program { private int value = 0; static void Main(string[] args) { var p = new Program(); p.Recursive(...); Console.WriteLine(p.value); } void Recursive(...) { value++; } } } 
    • Can you explain for ref and out - are they applicable in this case? - e1s
    • @ e1s theoretically you can use ref , but it will be "too". Usually, if you need to change the value of a variable, get a field. out will not help, because you need to have a value for all calls, and out will reset it after each call. - andreycha
    • And what all the global state pulls to change? Than method arguments did not please? - Sergey Teplyakov

    Why if I declare this method without static, does the program require an instance?

    The non-static method requires an instance because all non-static methods require an instance. I do not even know how to explain in more detail. This is about how to explain why the water is wet.

    How to make this copy?

    Object instances are typically created with the new operator.

    If through new Program (), then what will happen to the void Main?

    And what should happen to void Main?

      What to do in this case?

      You can declare a static field of class Program .
      For example:

       class Program { static int myField; static void Main(string[] args) { Recursive(...) } static void Recursie(...) { // тут доступно поле myField } } 

      Why if I declare this method without static , does the program require an instance?

      Answer: by definition. At the household level, I can formulate it like this:

      • Static methods are accessed by type name. Example:

         string s = "..."; bool b = String.IsNullOrEmpty(s); // <- вызов статического метода `String.IsNullOrEmpty` 
      • Reversal to non-static methods is carried out by reference to the type instance. Example:

         string s = "..."; string t = s.Trim(); // <- вызов нестатического метода для экземпляра `s` 

      How to make this copy?

      An instance is always created using the new operator. However, in some cases, this operator may not appear in the code explicitly. For example:

       int i = 0; string s = "..."; double[] d = { 0.0, 1.0, 1.5 }; 

      The list is far from complete.

        I do not agree with the tips that offer to pull the state through the field.

        Similar side effects, especially at the level of the type, not the object - this is bad from the point of view of understanding the inputs / outputs of the method.

        After all, nobody canceled the classics. A recursive method typically pulls state through method arguments. This is how we get stateful programming in FP.

        This is true, there is a problem. Because the condition states that the method must return void, this means that it must either display something on the screen (or otherwise show the result of its work) or change the state of the external world in some other way (write something in the database, or change the static field).

         static void Recurse(int state) { // Первое граничное условие if (state == 0) { Console.WriteLine("Все, приехали!"); return; } // Первый способ сокращения задачи if (state < 10) { Console.WriteLine("Recurse. State: {0}", state); Recurse(state - 1); return; } Console.WriteLine("state слишком большой! Уменьшаем его на 10!"); Recurse(state - 10); } void Main() { Recurse(25); } state слишком большой! Уменьшаем его на 10! state слишком большой! Уменьшаем его на 10! Recurse. State: 5 Recurse. State: 4 Recurse. State: 3 Recurse. State: 2 Recurse. State: 1 Все, приехали! 
        • If we are talking about FP, then void-methods are practically excluded. It seems to me that you shouldn’t be afraid to change the method signature so that it gets a state and returns a new state. - VladD
        • Yes, in the OP void methods (especially in the pure) can not be at all. But dragging the fields where you can get by with the parameters is also not worth it. - Sergey Teplyakov
        • Yeah, I actually meant to make state not a field, but a local variable / parameter / return value. - VladD