que-son-metodos-variables-estaticos-en-programacion

What are static variables and methods

  • 7 min

Static variables and methods are those that belong to the class itself, rather than to individual instances of the class.

This means there is a single copy of each static variable or method, shared by all instances of that class.

To give an example, if you had a Person class and each instance had its own book containing its personal data, static variables and methods would be a large shared whiteboard that everyone can read from and write to.

poo-variables-metodos-estaticos

All people share the common whiteboard

Static methods represent an approach to procedural programming without straying too far from object-oriented programming paradigms. Meanwhile, static variables are somewhat similar to “global variables.”

They are also slightly more convenient to use than instance ones because they don’t require creating an instance before using them.

Static Variables and Methods

Static Variables

Static variables belong to the class. This means there is a single copy of the variable, shared by all instances of the class.

Any method, both instance and static, can potentially access the variables (as long as the access modifiers allow it).

Static variables can be used to store data that must be accessible to all instances, to maintain global state, or for constants.

Static Methods

Static methods are functions that belong to the class and not to an instance of the class.

These methods cannot access instance variables or methods directly, because for them instances do not exist (they can access other static variables and methods).

Practical Case

Let’s return to the practical case of the Person class we had when discussing instance variables and methods. This time, we have added a static variable Counter and an example static method IncrementCounter().

Persona
  • stringNombre
  • stringDni
  • static intContador
  • static voidIncrementarContador()

First, from anywhere in the code I can access static variables and methods. That is, it’s possible to do this from anywhere,

Person.Counter = 12;
Person.IncrementCounter();
Copied!

Of course, “from anywhere” implies that all instances can equally access the variables. Even within the class definition itself.

In fact, one typical example of static variables and methods is adding a counter that counts the instances we generate of a class (we’ll see later that this is not a good idea 🙅‍♂️, except for making an example).

If we wanted to do that, we would simply increment the static variable Counter in the Person constructor.

class Person 
{
	Person()
	{
		Person.Counter++;

		// we could also call the static method
		//Person.IncrementCounter();
	}
}
Copied!

Which, as I said, is not the best idea in the world, but it illustrates well how we can use static variables and methods from anywhere in the code.

Examples in Different Languages

Finally, let’s see how different languages implement the concept of static variables and methods.

In C#, static variables and methods are defined using the static keyword.

public class Counter
{
    // Static variable
    public static int Counter;

    // Static method
    public static void IncrementCounter()
    {
        Counter++;
    }
}

// Usage
Counter.IncrementCounter();
Console.WriteLine(Counter.Counter);
Copied!

In C++, static variables and methods are defined using the static keyword.

#include <iostream>

class Counter {
public:
    // Static variable
    static int Counter;

    // Static method
    static void IncrementCounter() {
        Counter++;
    }
};

// Definition of the static variable
int Counter::Counter = 0;

// Usage
int main() {
    Counter::IncrementCounter();
    std::cout << Counter::Counter << std::endl;
    return 0;
}
Copied!

In JavaScript, static variables and methods are defined using the static keyword. These variables and methods belong to the class rather than to individual instances of the class.

class Counter {
    // Static variable
    static counter = 0;

    // Static method
    static incrementCounter() {
        Counter.counter++;
    }
}

// Usage
Counter.incrementCounter();
console.log(Counter.counter);
Copied!

In TypeScript, static variables and methods are defined using the static keyword.

class Counter {
    // Static variable
    static counter: number = 0;

    // Static method
    static incrementCounter(): void {
        Counter.counter++;
    }
}

// Usage
Counter.incrementCounter();
console.log(Counter.counter);
Copied!

In Python, static variables and methods can be simulated using @classmethod decorators and class variables.

class Counter:
    # Static variable
    counter = 0

    # Static method
    @classmethod
    def increment_counter(cls):
        cls.counter += 1

# Usage
Counter.increment_counter()
print(Counter.counter)
Copied!

Best Practices Advice

The million-dollar question with static methods is: When do I use a static method and when do I not? And throughout your life, I can tell you that you will change several times between loving them and hating them😘.

In principle, my advice is to avoid static methods and variables whenever possible. The main reason is that you cannot override them, nor can you easily replace them nor… (basically they don’t give you much flexibility).

Once your code “hooks” onto a static method, you are very tightly bound to it. That means they will cause maintainability problems in the future, testing problems, making mocks… they will cause all sorts of problems.

MyClass.DoSomething();  // once you put that in, you have to live with it forever
Copied!

Furthermore, most of the time it doesn’t make sense to use them. In the example we gave, which is the typical one used, of a counter that counts the number of Person instances created… well, in real life that’s a mess.

If you’re going to do something like that, the logical thing is to have a superior object PersonManager or PersonGroup, or whatever, that contains that information which is typically used in examples to illustrate static variables and methods.

public class PersonManager
{
	public int Counter;
	
	public Person GeneratePerson() {
		//.. whatever 
	}
}
Copied!

However, we also cannot deny that static methods bring simplicity to programs. For example, imagine you make a library that downloads videos from the Internet. A static method might be easier to use.

// it's easier to use this
VideoDownloader.Download("video_url");

// than this
var videoDownloader = new VideoDownloader();
videoDownloader.Download("video_url");
Copied!

In short, my advice is to avoid static methods as much as possible. Only use them if they make sense for the original purpose, which is very isolated functions that do not require their own variables or information.

The typical example is a class with mathematical functions, where you simply want to have the functions grouped, but it’s basically still procedural programming. There, it makes sense for them to be static.

Or, when you want to offer a simpler way for the developer to use a library. And usually always as a shortcut to an alternative method that offers more functionality.