Posted 25 February 2014 - 11:24 PM
RAII is about creating objects that are ready to use.
Being ready to use does NOT mean that it is hooked up to resources, that it has allocated blobs of memory, that it is attached to other objects, or otherwise integrated into the rest of the system.
When I create a std::vector I expect an empty object that is ready instantly that I can fill up at my convenience. When I create a std::ifstream I expect an object that is not yet attached to a file, but can be attached later, and I expect it to be instantly available, ready for use.
From another thread, when I create a network socket I expect an unconnected and empty stream to be available instantly, ready for use.
From another thread, when I create a logger I expect a fully-built logging class, but I expect it to come back instantly; it is initially connected to zero output streams and requires no resources, but is ready for use.
From another thread, when I create a generic game object I expect a fully built but completely empty game object, instantly available for use.
Going back through each:
When I create a vector there might be an optional constructor that does more work, but it isn't strictly necessary; by default I instantly get an empty object that is fully initialized to empty.
When I create a network socket there might be an optional constructor that attaches to the server and does some work, but it isn't strictly necessary; by default I instantly get an object that is fully initialized to a disconnected state.
When I create a logger there might be an optional constructor that accepts existing listening streams and hooks them up, but it isn't strictly necessary; by default I instantly get an object that is fully initialized to an empty listener state.
When I create a specific game object or an array of game objects, I absolutely DO NOT WANT each of those constructors to spawn off calls to load models from disk and into the cache system, to load textures from disk and into the cache, to load animations from disk, to load audio from disk, to integrate all of them into the rendering engine, to position them in the spatial trees, and so on. If I created an array of 50 game objects I might be looking at multiple seconds before the constructor returns to me, and it is doing an awful lot more than just constructing an empty object immediately. By default I instantly get an object that is fully initialized to an empty state.
Object lifetimes are generally more complex than a simple creation and destruction process. Often there is a fully constructed empty state (the default constructor) that is available instantly. There are often various levels of connectedness within the system. Maybe an SQL connection has states of disconnected, waiting for connection to the server, logging in, waiting for credentials, transmitting commands, waiting for results, and busy with communications. Maybe your game object has empty, proxied and out of world, proxied and in world, loaded out of world, loaded in world, active, disabled, in use, and assorted other states.
RAII means to initialize things to be ready to use. "Empty" and "Disconnected" are perfectly valid definitions of ready to use, and for non-trivial objects are usually the best default.
This question has been coming up a lot lately, so sorry if I sound too repetitive for this answer.