Please see my question below :
type 'data2' is defined :
typedef struct data2
{
int m;
float n;
} data2;
data1 is defined :
typedef struct data1
{
int a;
float b;
data2 *d2 // pointer to a data2 type
} data1;
I have a function with 3 arguments :
void func(data1 *x, data2* y, char z)
{
.
.
.
}
I can also write this function as
void func(data1 *x, char z)
{
data2 *y = x->d2
.
.
.
}
I use the function 'func' millions of times,
which implementation from the above two, will be quicker ?
(the first variation allocates 3 places on the stack, the second only
2, but it also has an extra line for assigning the pointer of data2)
Thanks :-)
Bob
The only way to be sure is to measure -- and even then, your
measurement with one machine and compiler and O/S may come out
differently than in other environments.
But let's guess: "Millions of times," you say. Okay, assume
that's ten million calls. And let's assume the time difference
(one way or the other) amounts to, oh, three hundred CPU cycles
per call (that's the approximate cost of an uncached RAM reference).
Finally, let's assume a 3GHz CPU. Put it all together, and one
version is a whopping ONE SECOND slower than the other. YMMV
with different assumptions, of course, but how many hoops are you
prepared to jump through for the sake of ONE SECOND? (How many
times must you run the program before those ONE SECOND gains add
up to enough to repay the time you put into saving them?)
> (the first variation allocates 3 places on the stack, the second only
> 2, but it also has an extra line for assigning the pointer of data2)
Beware of making assumptions about how the compiler maps your
source code to machine resources. It is possible, for example,
that the code will use *no* stack memory at all, if the compiler
can manage to keep things in CPU registers and such.
Besides, *somebody* needs to acquire the data2 pointer. If
there's a cost for doing it inside func(), there's probably also
a cost for doing it at the point of call. Just moving the cost
from one place to another won't make your program as a whole any
faster or slower. It's possible that there's an extra cost for
passing an extra argument -- but on the other hand, the caller
may already have the data2 pointer ready to hand, avoiding the
(apparent) memory reference inside func() ... Measure.
My recommendation is that you organize your data in a way
that makes good sense for the problem you're trying to solve, and
don't bend it all out of shape for the sake of tiny efficiencies.
--
Eric Sosman
eso...@ieee-dot-org.invalid
There is also a fundamental difference between the two methods.
The first method implies that it might not be necessary that data2
point to the same place as data1->d2:
data1 *x;
data1 *y;
...
func( x, y->d2, ...);
If this is not to be allowed, I would ALWAYS use the second method, so
that the function could not be called incorrectly.
--
Fred K
Probably one with less levels of indirection, in your
case, same. You have two pointers, depending on if those
structures are in cache or not, you can gain or loose
performance in situation where CPU is much faster
then BUS.
So if you don;t have many structures and all are in cache,
you will not notice performance difference.
Also if you access your structures in certain order.
So those functions are irrelevant, rather what
is relevant is how many of structures there are,
and how you access them.
> (the first variation allocates 3 places on the stack, the second only
> 2, but it also has an extra line for assigning the pointer of data2)
>
You concern is on architectures where CPU is fast as memory.
> Thanks :-)
>
> Bob
Greets
Sometimes online sometimes not
Thank you very much for your answers :-)
Bob