Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why won't this static variable increment when using generics?

I need a certain class to contain a static member that keeps track of everytime an instance of that class is instantiated, essentially so that each instance of the class has a unique index. It works with a non-generic class but this generic implementation fails whenever the type T differs between instances:

class A<T> {    private static int counter;     private static int Counter {        get {            Increment();            return counter;         }    }     private static void Increment() {        counter++;     }     public int Index;      public A()    {        this.Index = Counter; // using A<T>.Counter makes no difference         Console.WriteLine(this.Index);          } }   class Program {     static void Main(string[] args)     {         var a = new A<string>();         var b = new A<string>();          var c = new A<string>();         var d = new A<int>();      } } 

The output is:

1

2

3

1

As soon as the type T switches to int instead of string, the counter resets.

Does this fail by design, and if so what is the reason or how can I get around it? Or is it a bug? It makes sense to some degree because the type T, being generic, is in the class declaration, but..

like image 985
Sean Thoman Avatar asked Nov 15 '11 22:11

Sean Thoman


People also ask

Can we increment value of static variable?

Using a static variable will create one copy of the count variable which will be incremented every time an object of the class is created. All objects of the Counter class will have the same value of count at any given point in time.

Can generic variables be static?

Using generics, type parameters are not allowed to be static. As static variable is shared among object so compiler can not determine which type to used. Consider the following example if static type parameters were allowed.

Can I increment a static variable in C?

This is because the static variable retains the value after the increment even when the function block ends. Data segments are used to allocate a static variable and not stack segments. Static variables by default have some values with which it is initialized if not explicitly initialized.


1 Answers

Each different T creates a new class for A<T> and hence distinct static counters.

To get around this you can use inheritance like so:

abstract class A {    protected static int counter; }  class A<T> : A {    private static int Counter {        get {            Increment();            return counter;         }    }     private static void Increment() {        counter++;     }     public int Index;      public A()    {        this.Index = Counter;         Console.WriteLine(this.Index);          } } 
like image 141
Enigmativity Avatar answered Oct 17 '22 11:10

Enigmativity