Victor Bazarov wrote:
Chad Zalkin wrote: We are evaluating some old code that was written as part of our math
library.
This code uses some optimizations that I'm not sure are necessary or
safe, but is a source of debate between my coworkers.
Method 1 includes a temporary storage varriable at class scope.
Method 2 includes a temporary storage varriable at method scope.
Method 3 includes a temporary static storage varriable at method scope.
Are any of the methods better than the others in terms of speed and
thread safety?
This question is _better_ asked in a newsgroup that actually deals with
threading: comp.programming.threads. C++ does not have support, not does
it have any definitions of, threading. The program is assumed to be
single-threaded in C++ standard.
Now, when talking about threads it is essential to identify the data that
can be changed. You didn't say how many threads are accessing what part
of data at some point.
I don't believe method 1 or 3 are thread safe, but I think method 2 may
be too slow for a high-performance library. Is there a method 4 that
we should evaluate?
As an aside, I can't find in the standard where static is addressed in
terms of a member function. Is it true that a static varriable within
a member function exists for all instances?
A static object is a static object regardless of what scope it's in. It's
essentially a singleton.
/// ---- method 1
class vector {
...
private:
vector tempVector;
You simply _physically_ cannot have an object that contains an instance of
its own type.
};
vector::somefunction() {
Does this one have any return value type?
// writes to tempVector as temporary storage
It is generally _unknown_ here what storage duration 'tempVector' has,
since its storage duration is the same as that of '*this' object. (All
that assuming that the type of 'tempVector' is _not_ the same as the
object that contains it)
}
/// ---- method 2
class vector {
...
};
vector::somefunction() {
vector tempVector;
// writes to tempVector as temporary storage
This is the most "thread-safe", largely because in many threading models
(if not all), automatic variables are "per-thread".
}
/// --- method 3
class vector {
...
};
vector::somefunction() {
static vector tempVector;
// writes to tempVector as temporary storage
This is the _least_ "thread-safe", since static objects are usually shared
between all threads.
}
To sum up: method 2 is generally thread-safe, method 3 is generally not,
and nothing can be said about method 1.
V
In defence of my own sanity, method 1 was not meant to include itself.
Let's all imagine that the tempVector is now of type foo in all
methods.
The part that I forgot to mention in my haste was that more than one
method will use the temporary storage:
class vector {
void add(); // needs temporary storage
void sub(); // needs temporary storage
void dot(); // needs temporary storage
};
class tempStorage
{
public:
// some data members
};
Now, let's ignore the threadding issue since it is OT.
If add(), sub(), and dot() all need to store some temporary data during
their runtime,
is it more efficient to store this data at class level (constructing
and destructing once per object) or at function level (constructing and
destructing once per function call; potentially many more times).
Since add(), sub(), and dot() do not call each other, storing the data
at class level becomes possible. (But then the thread issue comes into
play...)
What are the pro's and con's of scoping at each level? What can I
trust the compiler to be allowed to optimize? What can I do to help
the compiler optimize?
Thanks for any insight!