Why would I want to use a static variable in a function in C++?

As I am working on a web application, I'm faced with a problem which is to at least most of the time, attempt to avoid accessing the database. This means reading certain data once and keep it in memory forever (until the process dies at which time the data can be lost, obviously, this is done the Unix way: process runs to generate the results and dies immediately once the result was produced.)

So, my general idea is to create a field in my C++ class and if necessary have a flag to know that the field was defined (i.e. some fields may remain the same even after we read the data so the problem would not be solved if it were for an extra flag.)

In general, this looks like this:

class Obj
{
public:

    int get_that_integer()
    {
        if(!m_int_defined)
        {
            m_int_defined = true;

            m_that_int = read_db("from here");
        }
        return m_that_int;
    }

private:
    bool m_int_defined = false;
    int m_that_int = 0;
};

There is one potential problem with such a definition. All the functions defined in your class now have access to the m_that_int value, but they are likely to forget to call get_that_integer() at least once to make sure that the variable is defined. That creates bugs, obviously.

One solution is to create sub-classes that hold the data and then you have to call a function to get it. That's quite a bit of extra work.

Another solution is to write unit tests. If the tests fail, then you've got to go back and fix the problems. This is certainly a very good solution! It helps with redesigning lower level code and making sure that higher level code still functions as expected.

Now there is one more solution. Save the data in a static variable inside the function. That way it is not accessible from the outside:

    int get_that_integer()
    {
        static bool m_int_defined = false;
        static int m_that_int = 0;

        if(!m_int_defined)
        {
            m_int_defined = true;

            m_that_int = read_db("from here");
        }
        return m_that_int;
    }

Now the variable is safe. Many people say you should not use static, but in this case there is another great advantage. Imagine that the static variable is a more complex type of variable like a QMap or std::vector. That variable requires initialization before you can use it.

In other words, each time you instantiate Obj, you also instantiate all those variables, whether you are to use them or not. When it is static, you do have a small penalty because each time you call the function, the code checks a flag to know whether the static variables were initialized the first time you entered the function. However, if you have several hundred such variables and only end up using 10 or 15, that's still a huge saving.

Another plus, the variable is secure, contrary to a variable member which anyone can access at the wrong time.

There is, however, a couple of drawbacks to think about:

1) If you somehow need to update one of those static variables (reset them) then you either need a flag in the function call, which is a bit annoying. You can also make the variable global (well... in a no name namespace) and then other functions may end up accessing the data at the wrong time and you don't eliminate the initialization problem, just moved it to just before the main() function.

2) Unless you do a new to create the object on the heap (which can be somewhat slow in comparison to not using new), the object gets destroyed when the application exits. Also you end up with pretty much no control over the order in which those objects get destroyed. As long as you don't use one in the other, you should be good though.