bs@alice.UucP (Bjarne Stroustrup) (10/16/86)
/* here are some more timings showing function call costs: */ struct s { int a; virtual f1(); // virtual function f3() { a++; return a; } // calls will be inlined f4(); // member function }; s::f1() { a++; return a;} s::f4() { a++; return a;} f2(s* p) {p->a++; return p->a; } // ``normal'' function f5(register s* p) {p->a++; return p->a; } // register argument int (*pf)(s*) = &f2; main() { s a; register s* p = &a; // for (register int i = 100000; 0<i; i--) p->f1(); // for (register int i = 100000; 0<i; i--) f2(p); // for (register int i = 100000; 0<i; i--) p->f3(); // for (register int i = 100000; 0<i; i--) ; // for (register int i = 100000; 0<i; i--) p->f4(); // for (register int i = 100000; 0<i; i--) (*pf)(p); for (register int i = 100000; 0<i; i--) f5(p); } /* Times in seconds, that is, the time needed per iteration in microseconds: virtual member empty fct fct inline fct loop p->f1() f2(p) p->f3() p->f4() pf(p) f5(p) ; VAX11/750: 41 32 5 41 31 40 3 VAX11/785: 21 15 2 20 16 20 1 sun3: 8 6 1 8 7 7 1 AT&T 3B20: 20 16 4 18 18 18 2 Amdahl5860: 1.1 1.0 .2 1.0 1.1 1.0 .2 AT&T6300+ (s) 30 26 12 28 28 27 10 AT&T6300+ (l) 46 42 20 42 42 41 10 A 6300+ is an AT clone (small and large models used for pointers, long i). Release 1.1 was used except for the 6300+. There I used a toy. So (1) A virtual member call is as fast as a non-virtual member call. (2) A member call is as fast as an equivalent non-member call. (3) Inlining function calls can be very effective in speeding up code. (4) Declaring "this" a register argument in a function with only little use of "this" (as in the examples above) is a loss. (5) VAX function calls are relatively expensive (not news). Thanks to all who help time the examples. */