|
More C++ woes |
|
(13:58 15/6/2002) Phlamethrower (13:25 14/7/2001) Phlamethrower (13:27 14/7/2001) rich (12:44 17/7/2001) ToiletDuck (15:36 17/7/2001) alpha (03:13 18/7/2001) johnstlr (13:50 14/7/2001) Phlamethrower (14:32 14/7/2001) colin (11:49 20/7/2001) colin (13:58 15/6/2002) colin (11:39 20/7/2001)
|
|
Phlamethrower |
Message #4791, posted at 13:25, 14/7/2001, in reply to message #4790 |
Unregistered user
|
Hmmm... I seem to be having problems editing that post, i.e. it won't save the changes... It's meant to look like this: Here's a puzzler which I've come across while working on RGL (*cough* www.coderscauldron.com *cough*). It concerns the transformation matricies... #include <stdio.h> #include <stdlib.h> class rglTMat { public: float m[16]; rglTMat() {printf("rglTMat made @ %d\n",(int) this);} ~rglTMat() {printf("rglTMat killed @ %d\n",(int) this);} void null() { int i; for (i=0;i<16;i++) m[i]=0; } void ident() { m[0]=m[5]=m[10]=m[15]=1; m[1]=m[2]=m[3]=m[4]=0; m[6]=m[7]=m[8]=m[9]=0; m[11]=m[12]=m[13]=m[14]=0; } rglTMat operator+(rglTMat b) { rglTMat o; int i; for (i=0;i<16;i++) o.m[i]=m[i]*b.m[i]; return o; } rglTMat operator*(rglTMat b) { rglTMat o; int x,y,i; printf("Mul stage 1\n"); o.null(); printf("Mul stage 2\n"); for (x=0;x<4;x++) for (y=0;y<4;y++) for (i=0;i<4;i++) o.m[x+(4*y)]+=m[i+(4*y)]*b.m[x+(4*i)]; printf("Mul stage 3\n"); return o; } }; void main() { rglTMat a,b,c; printf("Stage 1\n"); a.ident(); b.ident(); printf("Stage 2\n"); c = a*b; printf("Stage 3\n"); } Why, when the above program is run, does it produce output similar to the following?
rglTMat made @ 68624 rglTMat made @ 68700 rglTMat made @ 68776 Stage 1 Stage 2 rglTMat made @ 68992 Mul stage 1 Mul stage 2 Mul stage 3 rglTMat killed @ 68992 rglTMat killed @ 68916 rglTMat killed @ 68852 Stage 3 rglTMat killed @ 68776 rglTMat killed @ 68700 rglTMat killed @ 68624 More rglTMat's are released than claimed! The first three claims and last three releases are presumably for 'a','b' and 'c', and the fourth claim is presumably for 'o'. The question is where do the two extra rglTMat's at 68916 and 68852 come from? Could it be a bug in GCC? The reason I came across this is that I've been having problems with memory leaks & heap corruption in RGL, so decided to write some functions to track objects as they are made and deleted. When I examined the log file, I'd released 30K more memory than I'd claimed! |
|
[ Log in to reply ] |
|
Phlamethrower |
Message #4792, posted at 13:27, 14/7/2001, in reply to message #4791 |
Unregistered user
|
Grr! why do the leading spaces on the lines vanish?!?! |
|
[ Log in to reply ] |
|
johnstlr |
Message #4793, posted at 13:50, 14/7/2001, in reply to message #4791 |
Unregistered user
|
More rglTMat's are released than claimed! The first three claims and last three releases are presumably for 'a','b' and 'c', and the fourth claim is presumably for 'o'. The question is where do the two extra rglTMat's at 68916 and 68852 come from? Could it be a bug in GCC?
I think you're seeing the effect of C++ creating and deleting temporary objects, although I'm a bit confused as to why you don't see more rgtlMat made messages. I hope someone steps in if I've got this wrong. rglTMat operator*(rglTMat b)
This creates a temporary object "b". If you don't pass by reference then the object is passed by value meaning C++ creates a new object on the stack and does a bitwise copy of your parameter. When the method exits the temporary object is killed - hence the extra message. A similar thing happens on return return o;
This creates a temporary object on the stack which is passed back to the caller before the bitwise copy into "c" is made. The object is then discarded after the copy. This tallies up with the output you're seeing. One of the "kills" after MUL STAGE 3 is for "o". The others are for "b" and the temporary return object. You really want to be careful with this as the creation of temporary objects in C++ is a real performance killer. Where possible I suggest always passing in parameters by reference (ie so "b" becomes a reference as opposed to a temporary object. I'll have to look up what you can do about the returned object later as I don't have any C++ references to hand. |
|
[ Log in to reply ] |
|
Phlamethrower |
Message #4794, posted at 14:32, 14/7/2001, in reply to message #4793 |
Unregistered user
|
You really want to be careful with this as the creation of temporary objects in C++ is a real performance killer. Where possible I suggest always passing in parameters by reference (ie so "b" becomes a reference as opposed to a temporary object. I'll have to look up what you can do about the returned object later as I don't have any C++ references to hand. That may be what's been causing the problems then. Once I rewrite the classes to use references, I should be able to make some sense of the log files. Thanks for the help |
|
[ Log in to reply ] |
|
rich |
Message #4795, posted at 12:44, 17/7/2001, in reply to message #4792 |
Unregistered user
|
Grr! why do the leading spaces on the lines vanish?!?! Because this is being viewed in a web browser, and HTML doesn't recognise leading spaces (or indeed any multiple spaces)?Try using character 160 (hard space) instead. ALT+Space on a RISC OS machine should do the trick. |
|
[ Log in to reply ] |
|
Mark Quint |
Message #4796, posted by ToiletDuck at 15:36, 17/7/2001, in reply to message #4795 |
Quack Quack
Posts: 1016
|
Isnt there a "raw" text thingy that you can use for the forums, a bit like in HTML?? |
|
[ Log in to reply ] |
|
alpha |
Message #4797, posted at 03:13, 18/7/2001, in reply to message #4796 |
Unregistered user
|
You should be able to use both <code> and <pre> without any problems. |
|
[ Log in to reply ] |
|
colin |
Message #4799, posted at 11:39, 20/7/2001, in reply to message #4798 |
Unregistered user
|
I think you're seeing the effect of C++ creating and deleting temporary objects, although I'm a bit confused as to why you don't see more rgtlMat made messages. I hope someone steps in if I've got this wrong.
Ok I'll try again - I found the preview option this time :-) You don't get the messages because they are created using the copy constructor tglTMat(const tglTMat&); unless you specify this it is created automatically for you and by default just does a bitwise copy. |
|
[ Log in to reply ] |
|
colin |
Message #4800, posted at 11:49, 20/7/2001, in reply to message #4794 |
Unregistered user
|
You really want to be careful with this as the creation of temporary objects in C++ is a real performance killer. Where possible I suggest always passing in parameters by reference (ie so "b" becomes a reference as opposed to a temporary object. I'll have to look up what you can do about the returned object later as I don't have any C++ references to hand. That may be what's been causing the problems then. Once I rewrite the classes to use references, I should be able to make some sense of the log files.
If speed is important the best way to avoid temporaries is to overload the x= operators ie void operator+=(const rglTMat& rhs); void operator*=(const rglTMat& rhs); etc. |
|
[ Log in to reply ] |
|
Phlamethrower |
Message #4790, posted at 13:58, 15/6/2002 |
Unregistered user
|
Here's a puzzler which I've come across while working on RGL (*cough* www.coderscauldron.com *cough*). It concerns the transformation matricies... #include <stdio.h> #include <stdlib.h> class rglTMat { public: float m[16]; rglTMat() {printf("rglTMat made @ %d\n",(int) this);} ~rglTMat() {printf("rglTMat killed @ %d\n",(int) this);} void null() { int i; for (i=0;i<16;i++) m[i]=0; } void ident() { m[0]=m[5]=m[10]=m[15]=1; m[1]=m[2]=m[3]=m[4]=0; m[6]=m[7]=m[8]=m[9]=0; m[11]=m[12]=m[13]=m[14]=0; } rglTMat operator+(rglTMat b) { rglTMat o; int i; for (i=0;i<16;i++) o.m[i]=m[i]*b.m[i]; return o; } rglTMat operator*(rglTMat b) { rglTMat o; int x,y,i; printf("Mul stage 1\n" o.null(); printf("Mul stage 2\n" for (x=0;x<4;x++) for (y=0;y<4;y++) for (i=0;i<4;i++) o.m[x+(4*y)]+=m[i+(4*y)]*b.m[x+(4*i)]; printf("Mul stage 3\n" return o; } }; void main() { rglTMat a,b,c; printf("Stage 1\n" a.ident(); b.ident(); printf("Stage 2\n" c = a*b; printf("Stage 3\n" } Why, when the above program is run, does it produce output similar to the following?
rglTMat made @ 68624 rglTMat made @ 68700 rglTMat made @ 68776 Stage 1 Stage 2 rglTMat made @ 68992 Mul stage 1 Mul stage 2 Mul stage 3 rglTMat killed @ 68992 rglTMat killed @ 68916 rglTMat killed @ 68852 Stage 3 rglTMat killed @ 68776 rglTMat killed @ 68700 rglTMat killed @ 68624 More rglTMat's are released than claimed! The first three claims and last three releases are presumably for 'a','b' and 'c', and the fourth claim is presumably for 'o'. The question is where do the two extra rglTMat's at 68916 and 68852 come from? Could it be a bug in GCC? The reason I came across this is that I've been having problems with memory leaks & heap corruption in RGL, so decided to write some functions to track objects as they are made and deleted. When I examined the log file, I'd released 30K more memory than I'd claimed! |
|
[ Log in to reply ] |
|
colin |
Message #4798, posted at 13:58, 15/6/2002, in reply to message #4793 |
Unregistered user
|
I think you're seeing the effect of C++ creating and deleting temporary objects, although I'm a bit confused as to why you don't see more rgtlMat made messages. I hope someone steps in if I've got this wrong. You don't get the messages because they are created using the copy constructortglTMat(const tglTMat& unless you specify this it is created automatically for you and by default just does a bitwise copy.
|
|
[ Log in to reply ] |
|
|