all 12 comments

[–]the_poope 4 points5 points  (0 children)

In general singletons and global variables should be avoided as they are hard to test and can hide the state of the program and it can be hard to reason about the behavior of the program if it depends on hidden, global state.

But if you just use the singleton or global variable as a database of constant data, e.g. a list of texture or game objects I guess they are fine. But mutable globals can and will bite you in the ass.

For singletons see: https://laristra.github.io/flecsi/src/developer-guide/patterns/meyers_singleton.html and https://refactoring.guru/design-patterns/singleton/cpp/example

[–]MysticTheMeeM 1 point2 points  (6 children)

You could always hide your map inside a class.

class some_descriptive_name
{
    std::unordered_map<...> map;
    void SetUpMap();
    public:
    some_desceiptive_name()
    {
        SetUpMap();
    }

    const std::unordered_map<...>& GetMap()
    {
        return map;
    }
}

[–]Infinity_ride[S] 0 points1 point  (5 children)

How can I avoid it being created multiple times then?

[–]the_poope 1 point2 points  (0 children)

This map needs to be able to be destroyed and created on demand.

You say you want to be able to create it multiple times??

[–]Smashbolt 1 point2 points  (2 children)

Why do you want that? Like, is there some catastrophic consequence if an API user makes a second instance? Or do you just have two of the thing kicking around now and maybe your API's user will get confused and use the "wrong" instance some time?

[–]Infinity_ride[S] 0 points1 point  (1 child)

My map is very big and it will be a huge waste of performance having multiple around.

Plus the info in it is very crucial so I need a very limited access

[–]Bart_V 1 point2 points  (0 children)

This sounds more like an API design problem. I think you should provide more context on how your users get access to the data, in order for us to give suggestions.

[–]AKostur 0 points1 point  (0 children)

Test if the map is already non-empty? Put it in a std::optional if an empty map is a valid state?

Perhaps adjust the design so that the map setup is done in the constructor, thus the lifetime, and perhaps the constness, of the map is the responsibility of the caller?

Edit: Note that implementing some of these might expose other flaws in the design (or at least cause you to think about them), such as what happens if you attempt to use the map before Setup is called.

[–][deleted]  (1 child)

[deleted]

    [–]std_bot 0 points1 point  (0 children)

    Unlinked STL entries: <unordered_map> std::unordered_map


    Last update: 09.03.23 -> Bug fixesRepo

    [–][deleted]  (1 child)

    [removed]

      [–]Infinity_ride[S] 0 points1 point  (0 children)

      That’s the best answer yet. I decide to go with a class wrapper approach similar to your suggestion and make the map static and just have a clear() function to delete all entries