Subject: Re: [boost] [filesystem] windows/posix inconsistencies.
From: Ion Gaztañaga (igaztanaga_at_[hidden])
Date: 2012-01-31 15:37:59
El 31/01/2012 14:47, Stephan T. Lavavej escribió:
> [Thorsten Ottosen]
>> However, consider
>> const std::string& ext = iter->path().extension().string();
>> This is fine on windows, as a temporary is returned, and its lifetime is
>> extended; on linux, extension() returns a temp path object, from where
>> we get a reference. I'm not a 100% sure, but I think the C++ standard
>> does not guarantee that this path object be kept alive.
> * The Standard requires the temporary path to be destroyed at the semicolon.
> * Replace string with wstring, and this becomes problematic on Windows.
> * Additionally, returning const values like const string/const wstring inhibits move semantics.
I know I repeat myself too many times, but I can't resist! One of the
issues I find with move semantics is that sometimes we assume returning
by value is free. Returning by value objects with dynamic allocation
avoids reusing those dynamic resources (specially in loops). I think
returning by value has a nice syntax and properties (you don't need a
default-constructed object when you need to create a new object instead
of assigning it), but IMHO is premature pessimization.
Although returning vectors by value might be a good idea for factories,
and such things, it's always more efficient to pass a reference to a
vector, and clear() + fill or assign, or even better, reusing already
constructed values (which can be vectors of vectors). Using
filesystem::path in a loop might trigger a lot of allocations that could
be avoided if the string could be passed as an argument, reusing already
allocated memory for each path.
In this question I totally agree with Alexandrescu (skip until 41:00 if
downloaded, or 1:41:00 in the online video according to my web browser):
Apart from the arguments explained by Alexandrescu and Meyers, I'd say
that you must also avoid returning by value objects without dynamic
allocation but big sizeof(T) (say std::array<T, 1000>, instead of
returning std::vector<T>(1000)), you are going to waste a lot of stack
space with that extra temporary.
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk