Re: [Dev-C++] differnece between system pause and cin.get()
Open Source C & C++ IDE for Windows
Brought to you by:
claplace
|
From: Per W. <pw...@ia...> - 2003-02-18 09:33:53
|
On Tue, 18 Feb 2003, Ioannis Vranos wrote:
> -------Original Message-------
>
> From: Per Westermark
> Date: =D4=F1=DF=F4=E7, 18 =D6=E5=E2=F1=EF=F5=DC=F1=E9=EF=F2 2003 9:42:16 =
=F0=EC
> To: Ioannis Vranos
> Cc: Dev-C++ Mailing List
> Subject: Re: [Dev-C++] differnece between system pause and cin.get()
>
> For register calling convention, the this pointer may be sent for free
> from one member of the class to another member of the class, since the
> register will already be initialized with this. For stack calling
> convention, it HAS to take extra time, since it's an extra 32-bit put pus=
h
> on the stack. Also, with register calling, the first call HAVE to take
> extra time, since the compiler must load the address of the object before
> making the call.
>
>
> =3D=3D> Ok, so in few words you are telling that the regular function cal=
ls have
> an additional extra cost because of the stack calling convention, while
> member functions have that time cost only at the first call when it fetch=
es
> it from memory to register. So we agree.
1 - You may not assume that the this ptr is always sent in registers.
Depending on compiler and compiler options, it might always be sent on
stack as a regular but hidden parameter.
2 - Regular function calls doesn't have a this ptr, so no time used to
send a this ptr. Member function always have this ptr, so depending on
calling convention, time is needed on all calls, or on only the first
obj->member() but not when member() calls member2().
>
>
>
> Member functions always have a regular address. Your description of call
> through an offset in an array is the special case of a call to a virtual
> method.
>
>
> =3D=3D> No, no, no. Try assigning a member function to a pointer for a re=
gular
> function. Try to print the "address" of a member function. The standard d=
oes
> not restrict how member functions are implemented, only that they cannot =
be
> expected to be regular functions. Usually, member functions are called
> through an offset of an array.
This is just a protection the C++ compiler adds, since a normal pointer
call would not know about a this ptr. If you program from assember - or if
you know the full decorated name of the member function, you may still
have a pointer directly to the method and call it directly. But then Your
code most manually make sure that the hidden 'this' parameter is sent
accurding to current calling convention.
>
>
> However, the constructor for the same class may still call
> directly without going to the VMT (Virtual Method Table). A call through
> the VMT is slower, since the compiler first have to load the VMT table
> address as an offset from the this pointer, and then do the call from an
> offset into the table.
>
> If you don't believe me, just ask the compiler to emit assembler output
> and have a peek.
>
>
> =3D=3D> You are out of range for me. :) I do not know assembly almost at =
all and
> i am telling only what i have read/learned. But since we know C++ we can =
do
> the test:
I already mentioned the case below in the previous mail, i.e. code quality
of regular C-style call with a manual THIS ptr is often a bit slower due
to less optimization in compiler. The important thing is that a regular
function most of the time doesn't NEED the THIS ptr, while all non-static
member fuctions MUST have it.
> #include <iostream>
> #include <ctime>
> #include <limits>
> #include <cstdio>
>
> class something
> {
> unsigned long x;
>
> public:
> something(int y=3D0):x(y) {}
>
> void test();
> friend void testf(something &);
> };
>
>
>
> int main()
> {
> using namespace std;
>
> clock_t t1, t2, t3, t4, temp;
>
> unsigned long i;
>
> something blade;
>
> cout<<"Number of iterations for each kind: "<<numeric_limits<unsigned
> long>::max()/20<<endl;
>
>
> for (t1=3Dtemp=3Dclock(); !(t1-temp); t1=3Dclock())
> ;
>
>
> for(i=3D0; i<numeric_limits<unsigned long>::max()/20; i++)
> blade.test();
>
> t2=3Dclock();
>
> cout<<"Time consumed by "<<numeric_limits<unsigned long>::max()/20<<" ca=
lls
> of void something::test(): ";
> cout<<static_cast<double>(t2-t1)/CLOCKS_PER_SEC<<endl;
>
>
> for (t3=3Dtemp=3Dclock(); !(t3-temp); t3=3Dclock())
> ;
>
> for(i=3D0; i<numeric_limits<unsigned long>::max()/20; i++)
> testf(blade);
>
> t4=3Dclock();
>
> cout<<"Time consumed by "<<numeric_limits<unsigned long>::max()/20<<" ca=
lls
> of void testf(something &): ";
> cout<<static_cast<double>(t4-t3)/CLOCKS_PER_SEC<<endl;
>
> }
>
>
> void testf(something &x) { x.x++; }
>
> void something::test() { x++; }
>
>
> =3D=3D> This code in my system produces:
>
> C:\c>temp
> Number of iterations for each kind: 214748364
> Time consumed by 214748364 calls of void something::test(): 0.45
> Time consumed by 214748364 calls of void testf(something &): 0.461
>
>
> The difference is very slight, negligible. However after repeative runs,
> testf() consistently remains the slower:
>
> C:\c>temp
> Number of iterations for each kind: 214748364
> Time consumed by 214748364 calls of void something::test(): 0.45
> Time consumed by 214748364 calls of void testf(something &): 0.461
>
> C:\c>temp
> Number of iterations for each kind: 214748364
> Time consumed by 214748364 calls of void something::test(): 0.45
> Time consumed by 214748364 calls of void testf(something &): 0.481
>
> C:\c>temp
> Number of iterations for each kind: 214748364
> Time consumed by 214748364 calls of void something::test(): 0.45
> Time consumed by 214748364 calls of void testf(something &): 0.481
>
> C:\c>temp
> Number of iterations for each kind: 214748364
> Time consumed by 214748364 calls of void something::test(): 0.45
> Time consumed by 214748364 calls of void testf(something &): 0.481
>
>
>
>
> Bottom line: As I said on my original mail, member calls are slower than
> regular calls, but these extra nanoseconds might be ignored for just abou=
t
> all programs out there, since the majority of the runtime is in other
> parts of the program.
>
>
> =3D=3D> I disagree, but that's life.
>
>
>
> Ioannis Vranos
>
> * Programming pages: http://www.noicys.freeurl.com
> * Alternative URL: http://run.to/noicys
|