I've written up some stuff about why consting is good. It's in the
Parrot repository as cage/consting.pod.
To my old p5p homies: I send this to you so you don't forget about
consting while I'm working over here in Parrotland!
xoxo,
Andy
=head1 Why consting is good
In Perl, we have the C<use constant> pragma to define unchanging
values. The L<Readonly> module extends this to allow arrays and
hashes to be non-modifiable as well.
In C, we have C<const> numbers and pointers, and using them wherever
possible lets us put safety checks in our code, and the compiler
will watch over our shoulders.
=head2 C<const> numbers
The easiest way to use the C<const> qualifier is by flagging numbers
that are set at the top of a block. For example:
int max_elements;
max_elements = nusers * ELEMENTS_PER_USER;
...
array[max_elements++] = n;
/* but you really meant array[max_elements] = n++; */
Adding a C<const> qualifier means you can't accidentally modify
C<max_elements>.
const int max_elements = nusers * ELEMENTS_PER_USER;
=head2 C<const> pointers
If a pointer is qualified as const, then its contents cannot be
modified. This lets the compiler protect you from doing naughty
things to yourself.
Here are two examples for functions you're familiar with:
int strlen( const char *str );
void memset( char *ptr, char value, int length );
In the case of C<strlen>, the caller is guaranteed that any string
passed in won't be modified. How terrible it would be if it was
possible for C<strlen> to modify what gets passed in!
The const on C<strlen>'s parameter also lets the compiler know that
C<strlen> can't be initialzing what's passed in. For example:
char buffer[ MAX_LEN ];
int n = strlen( buffer );
The compiler knows that C<buffer> hasn't been initialized, and
that C<strlen> can't be initializing it, so the call to C<strlen>
is on an uninitialized value.
Without the const, the compiler assumes that the contents of any
pointer are getting initialized or modified.
=head2 C<const> arrays
Consting arrays makes all the values in the array non-modifiable.
const int days_per_month[] =
{ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
You don't want to be able to do C<days_per_month[1] = 4;>, right?
=head2 Mixing C<consts>
Combining C<const>s on a pointer and its constants can get confusing.
Note the difference between a pointer to constant characters:
/* Pointer to constant characters */
const char *str = "Don't change me.";
str++; /* legal, now points at "o" */
*str = "x"; /* not legal */
and a constant pointer to characters:
/* Constant pointer to characters */
char * const str = buffer;
str++; /* not legal */
*str = 'x'; /* buffer[0] is now 'x' */
Note the difference between which side of the asterisk that the
C<const> is on.
You can also combine the two, with a constant pointer to constant
characters:
const char * const str = "Don't change me";
or even an array of constant pointers to constant characters:
const char * const days[] =
{ "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" };
--
Andy Lester => [EMAIL PROTECTED] => www.petdance.com => AIM:petdance