c#: static variable in a static method
Asked Answered
C

3

54

Can you have a static variable in a static method? Would the value of this variable be preserved across all calls to the method?

eg.

public static void MyMethod()
{
    static int x = 0;
    x++;
}
Cozy answered 24/12, 2010 at 10:12 Comment(5)
Are you asking because you've used a Shared local variable before in VB.NET? This isn't natively supported by the CLR in any case, and VB.NET has to use some behind-the-scenes trickery to create this effect.Daub
What you need is a static class memberYeaton
@Colin - I think he wants x to be only accessible by MyMethod(), and not by any other methods regardless of whether they are in this class or not.Cocksure
possible duplicate of Does C# support the use of static local variables?Orsino
Anyone know if this has changed in 7 years. I vaguely recall that this either newly is, or potentially might be a new feature.Wintery
K
54

No.

You can't have local static variables.

From MSDN:

C# does not support static local variables (variables that are declared in method scope).

And here:

The static modifier can be used with classes, fields, methods, properties, operators, events, and constructors, but it cannot be used with indexers, destructors, or types other than classes.

As you can see, local variables are not mentioned.


You can, however use a static field:

public class MyClass
{
    private static int MyVariable = 10;

    public static void MyMethod()
    {
        MyVariable++;
    }
}
Kaki answered 24/12, 2010 at 10:13 Comment(4)
Unfortunate because if MyVariable is only used in MyMethod it belongs in MyMethod, not exposed to the rest of the class.Condonation
This is probably the single disadvantage of using C# in favor of an older "C" language. C++ scoping was weaker, but you could have local static variables. This is what make the strtok function even possible. From the POSIX strtok page: This function uses static storage to keep track of the current string position between calls. I wrote a variant of it in C++ that ignored empty records and accepted any delimiter that could be represented by a C++ String class. Knowing how these things work should make it replicate-able in any language, but alas, this is one weakness of C#.Incomprehensive
@JoelTrauger How exactly does C++ have weaker scoping rules than C#? As far as I can tell, they are identical, except that C++ may have local static variables.Xantha
IIRC, in C++ you have explicitly invoke inheritance to gain the properties of a class. Anything not explicitly passed forward through inheritance is automatically private. In C#, just make the class public and you automatically inherit all the public members of that class. C# also allows for internal scoping to further control the scoping of a class member. Because of that I consider C++ scoping to be weaker, though others might find it stronger...since static variables do not exist in C#.Incomprehensive
B
11

No, but you could have:

private static int x = 0;
public static void MyMethod()
{
     x++;
} 
Berndt answered 24/12, 2010 at 10:18 Comment(2)
I think you will mostly want [ThreadStatic]private static int x = 0; if you do that?Precinct
the issue is that it is likely in this kind of thing that you don't want x accessed directly by other parts of the class. I'm sure the answer would be "well just wrap everything in a static class then" But that seems like a lot of boilerplate.Dissepiment
S
1

Here is sort of a hackish way to accomplish what you're trying to do. Turn MyMethod into an Action that creates a closure on x. The variable x will only be visible to the innermost delegate, and behaves like a static variable. If anyone has any suggestions for improving this pattern let me know.

public static readonly Action MyMethod = new Func<Action>(delegate ()
{
    var x = 0;
    return delegate () { x++; };
}).Invoke();

//example usage:
public void Init() {
    MyMethod();
}
Studdingsail answered 16/1, 2022 at 5:5 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.