From: nilitonilito n. <nil...@ho...> - 2007-12-14 10:29:10
|
Hi all, The list being active again lately I've decided to start my own thread. For now 9 months I've been working as a C++ developer for a software compan= y (that's why my involvement as MusE developer has significantly dropped, a= fter programming all day long I need to get away from my PC more than befor= e). But the good point is that I'm learning how to produce healthier progra= ms. The little guy I'd like to talk about today is assert. At first I dislike t= o use it but I forced myself so my colleagues would think I'm a good progra= mmer ;). Guess what? I can't ever program again without using assert, this = little guy is fantastic! I use it all the time. For instance assume you need to access pointer ptr and in the current conte= xt ptr should be pointing towards a non null instance otherwise it does mak= e sense in the program and it could even crash it. then you just put an assert before using the pointer. Like : assert(ptr); //check that the pointer is non null ptr->method(blabla); //access the methods You can use assert for any properties you'd like to check in the course of = the program, like : assert(total_notes =3D added_notes - deleted_notes); Basically I ALWAYS use assert when the program could crash (like in my exam= ple with ptr), this prevents myself from hours of debugging. Besides preven= ting more crashing it also just gives hint to a reviewer of the code on the= assumptions that part of the code makes. assert is part of the C++ standard so you don't need to include any header,= you can use it right away. Of course it takes resources to treat all these assert but a flag to the co= mpiler makes it simply ignore them -DNDEBUG . As far as I remember there is no use at all of assert in the code of MusE. Hope my rumination would help at some point and thanks for reading it! Cheers Nil _________________________________________________________________ Microsoft vous offre un logiciel pour classer, retoucher et partager vos ph= otos ! http://www.windowslive.fr/galerie/= |
From: Mathias L. <mat...@da...> - 2007-12-14 10:37:13
|
nilitonilito nilitonilito skrev: > Hi all, > > The list being active again lately I've decided to start my own thread. > > For now 9 months I've been working as a C++ developer for a software > company (that's why my involvement as MusE developer has significantly > dropped, after programming all day long I need to get away from my PC > more than before). But the good point is that I'm learning how to > produce healthier programs. > > The little guy I'd like to talk about today is assert. At first I > dislike to use it but I forced myself so my colleagues would think I'm > a good programmer ;). Guess what? I can't ever program again without > using assert, this little guy is fantastic! I use it all the time. > > For instance assume you need to access pointer ptr and in the current > context ptr should be pointing towards a non null instance otherwise > it does make sense in the program and it could even crash it. > > then you just put an assert before using the pointer. Like : > > assert(ptr); //check that the pointer is non null > ptr->method(blabla); //access the methods > > You can use assert for any properties you'd like to check in the > course of the program, like : > assert(total_notes = added_notes - deleted_notes); > > Basically I ALWAYS use assert when the program could crash (like in my > example with ptr), this prevents myself from hours of debugging. > Besides preventing more crashing it also just gives hint to a reviewer > of the code on the assumptions that part of the code makes. > > assert is part of the C++ standard so you don't need to include any > header, you can use it right away. > > Of course it takes resources to treat all these assert but a flag to > the compiler makes it simply ignore them -DNDEBUG . > > As far as I remember there is no use at all of assert in the code of MusE. > Hope my rumination would help at some point and thanks for reading it! > > Cheers > Nil > I've actually seen it in a few places in MusE. Or at least one! :D Whether it's actually worth using or not is a discussion I will try to avoid. I guess it all comes down to how you use it, but I think suggestions like these are good. /Mathias |
From: Werner S. <ws...@se...> - 2007-12-14 12:26:42
|
Hi Nil, using assert macros is partly a matter of programming style and taste. My personal experience over many years of c++ programming show that they do not buy much. Your example shows were not to use an assert. The program will crash with and without the assert and you need a debugger to find out what happend anyway. Another tip to discover hard to find bugs is to use the "valgrind" tool. It can find the use of uninitialized variables which saved me _lots_ of time. Regards, Werner On Freitag 14 Dezember 2007, nilitonilito nilitonilito wrote: > > Hi all, > > The list being active again lately I've decided to start my own thread. > > For now 9 months I've been working as a C++ developer for a software company (that's why my involvement as MusE developer has significantly dropped, after programming all day long I need to get away from my PC more than before). But the good point is that I'm learning how to produce healthier programs. > > The little guy I'd like to talk about today is assert. At first I dislike to use it but I forced myself so my colleagues would think I'm a good programmer ;). Guess what? I can't ever program again without using assert, this little guy is fantastic! I use it all the time. > > For instance assume you need to access pointer ptr and in the current context ptr should be pointing towards a non null instance otherwise it does make sense in the program and it could even crash it. > > then you just put an assert before using the pointer. Like : > > assert(ptr); //check that the pointer is non null > ptr->method(blabla); //access the methods > > You can use assert for any properties you'd like to check in the course of the program, like : > assert(total_notes = added_notes - deleted_notes); > > Basically I ALWAYS use assert when the program could crash (like in my example with ptr), this prevents myself from hours of debugging. Besides preventing more crashing it also just gives hint to a reviewer of the code on the assumptions that part of the code makes. > > assert is part of the C++ standard so you don't need to include any header, you can use it right away. > > Of course it takes resources to treat all these assert but a flag to the compiler makes it simply ignore them -DNDEBUG . > > As far as I remember there is no use at all of assert in the code of MusE. > Hope my rumination would help at some point and thanks for reading it! > > Cheers > Nil > > > _________________________________________________________________ > Microsoft vous offre un logiciel pour classer, retoucher et partager vos photos ! > http://www.windowslive.fr/galerie/ |
From: nilitonilito n. <nil...@ho...> - 2007-12-14 13:02:40
|
Hi Werner, > From: ws...@se... > To: lmu...@li... > Date: Fri, 14 Dec 2007 13:26:24 +0100 > Subject: Re: [Lmuse-developer] sane programming >=20 > Hi Nil, >=20 > using assert macros is partly a matter of programming style and taste. > My personal experience over many years of c++ programming show that they > do not buy much. that is a matter of taste I guess and is probably more or less useful depen= ding on the way they are used (and also in which programming context). I ca= nnot say I'm a very experienced programmer (I've actually started to learn = C++ with MusE ;-) so I might change my mind over time but so far I have app= reciated there benefices in many occasions. > Your example shows were not to use an assert. The program will crash > with and without the assert and you need a debugger to find out what > happend anyway. yes indeed but the difference is that you immediately know where (and possi= bly why, if the assert happens to be self-explanatory enough) the program h= as crashed without even running a debugger. Some times I just see what asse= rt has been raised, go to that line and the fix is obvious, some other time= s of course I need to run a debugger. Some other times the program raises a= n assert (and the program would not have crashed) but reveals that somethin= g wrong is going on, that's equally useful. >=20 > Another tip to discover hard to find bugs is to use the "valgrind" tool. > It can find the use of uninitialized variables which saved me _lots_ of t= ime. yeah valgrind is a powerful debugger I've only recently learned to use as w= ell... Cheers, Nil _________________________________________________________________ Nouveau ! Cr=E9ez votre profil Messenger ! http://home.services.spaces.live.com/= |
From: Tim <ter...@us...> - 2007-12-15 01:13:02
|
If I may offer my opinion: I agree that we don't gain much by using assert, and I avoid it completely, because nothing pisses off a user more than having the program stop, whether due to an assert, or some other unpredicted cause. My style is that I keep the program running at all costs ! Only when the program could not possibly continue, do I quit with an assert or exit. It's called "mission critical". My 'golden rule' is this: I check if a pointer is null, and if it is, then I simply return from the function (with an error code, if allowed) AND do a 'printf()' so I can see on the command line that something went wrong. But NEVER just quit the program. "Mission critical" means you plan for such situations thoroughly, consistently, and gracefully throughout the program. Also, I would like to point out that if a function is passed a null pointer, well OK, that's easy to check, but most of the time it will be passed a BOGUS nonsense non-null pointer. You can't check such pointers. In some cases, yes, you can check if it's a valid pointer if there is a list of valid pointers somewhere and the pointer is not in the list. For example in Muse there is a list of 'track pointers'. If a function is passed a 'track' pointer, you can see if the pointer is in the list. But beyond that, there's no way to check such pointers by themselves, simply because attempting to de-reference them might crash the program. This is why asserting for null pointers is rarely effective ! All you need to do is start the program under a debugger, and the debugger will tell you where the violation occurred. No valgrind etc. is needed. ***----------------------------------------------------------*** While we are on the subject of programming style, I would like to alert the programmers out there to watch out for a particular Standard Template Library no-no: I call it the 'delete while iterating' bug: In Muse I had to fix several places where someone iterated an STL 'map' or 'list', and would conditionally delete items from the map or list, while still iterating the map or list. This is a no-no! The iterator becomes invalid after deleting an item, so the whole iteration has to be started over again. *** Take a look in Muse 0.9, in ./muse/seqmsg.cpp: around line 525: In the function Audio::msgRemoveTracks() Read the comments I placed in there. Learn it, use it ! Comments welcome! Cheers. Tim. |
From: Werner S. <ws...@se...> - 2007-12-15 09:02:27
|
On Samstag 15 Dezember 2007, Tim wrote: ... > ***----------------------------------------------------------*** > While we are on the subject of programming style, I would like to alert > the programmers out there to watch out for a particular > Standard Template Library no-no: I call it the 'delete while iterating' bug: > In Muse I had to fix several places where someone iterated an STL 'map' > or 'list', and would conditionally delete items from the map or list, while > still iterating the map or list. This is a no-no! The iterator becomes > invalid after deleting an item, so the whole iteration has to be started > over again. > *** Take a look in Muse 0.9, in ./muse/seqmsg.cpp: around line 525: > In the function Audio::msgRemoveTracks() > Read the comments I placed in there. Learn it, use it ! > > Comments welcome! Cheers. Tim. thats the reason i recently more use the Qt containers. Besides their nicer syntax they use (as most Qt objects) "copy on write" which also works with threads. For example in a "foreach" loop you iterate over a container copy. This allows deleting of items in the loop without problems. I found lot of situations were Qt containers are much easier to use than STL. Werner |
From: nilitonilito n. <nil...@ho...> - 2007-12-15 10:04:02
|
Hi Tim, > From: ter...@us... > To: lmu...@li... > Date: Fri, 14 Dec 2007 20:27:30 -0500 > Subject: Re: [Lmuse-developer] sane programming >=20 > If I may offer my opinion: > I agree that we don't gain much by using assert, and I avoid it > completely, because nothing pisses off a user more than having=20 > the program stop, whether due to an assert, or some other=20 > unpredicted cause. The user should not be bothered with asserts, in addition to crash the prog= ram they can also decrease its performance, that's why I mentioned the flag= -DNDEBUG... > My style is that I keep the program running at all costs ! > Only when the program could not possibly continue, do I > quit with an assert or exit. It's called "mission critical". > My 'golden rule' is this: I check if a pointer is null, and if it is,=20 > then I simply return from the function (with an error code, if allowed)= =20 > AND do a 'printf()' so I can see on the command line > that something went wrong.=20 > But NEVER just quit the program. "Mission critical" means you plan=20 > for such situations thoroughly, consistently, and gracefully throughout= =20 > the program. Yeah I see what you mean, I actually started to code that way, putting a te= st rather than an assert so the program doesn't stop but soon I realized it= s awkward consequences, a bug occurs and you have no idea what is wrong bec= ause the unexpected behavior would make its way through layers and layers o= f code (assuming you don't handle code errors properly of course). Then the= only way to locate the bug is to run a debugger and step each instruction = one by one and carefully check at each step if it behaves correctly, using = assert has the potential to alleviate that kind of wrong_behavior hunting. >=20 > Also, I would like to point out that if a function is passed a null point= er, > well OK, that's easy to check, but most of the time it will be passed > a BOGUS nonsense non-null pointer. You can't check such pointers. > In some cases, yes, you can check if it's a valid pointer if there is=20 > a list of valid pointers somewhere and the pointer is not in the list. > For example in Muse there is a list of 'track pointers'. If a function is= =20 > passed a 'track' pointer, you can see if the pointer is in the list. > But beyond that, there's no way to check such pointers by themselves, > simply because attempting to de-reference them might crash the program. > This is why asserting for null pointers is rarely effective ! If a null pointer can be passed to a method without necessarily breaking th= e code's assumptions then assert should not be used, or should be used so t= hat it captures what really breaks the assumptions like assert(!A || ptr); > =20 > All you need to do is start the program under a debugger, and the debugge= r=20 > will tell you where the violation occurred. No valgrind etc. is needed. Yes sure, my example from the start (with ptr) wasn't very good as using a = debugger would rapidly locate the error anyway. >=20 > ***----------------------------------------------------------*** > While we are on the subject of programming style, I would like to alert > the programmers out there to watch out for a particular=20 > Standard Template Library no-no: I call it the 'delete while iterating' = bug: > In Muse I had to fix several places where someone iterated an STL 'map'=20 > or 'list', and would conditionally delete items from the map or list, wh= ile=20 > still iterating the map or list. This is a no-no! The iterator becomes=20 > invalid after deleting an item, so the whole iteration has to be started= =20 > over again. Yeah I see, I've suffered days of debugging on DeicsOnze because of that ki= nd of careless coding attitude (that's when I started using STL without kno= wing much of what I was doing...). Cheers Nil _________________________________________________________________ Votre contact a choisi Hotmail, l'e-mail nouvelle g=E9n=E9ration. Cr=E9ez u= n compte.=20 http://www.windowslive.fr/hotmail/default.asp= |