OT: Programming in C

Les hlhowell at pacbell.net
Mon Apr 14 17:20:03 UTC 2008


On Mon, 2008-04-14 at 12:49 -0400, Steven W. Orr wrote:
> On Friday, Apr 11th 2008 at 17:19 -0000, quoth Bill Davidsen:
> 
> =>Matthew Saltzman wrote:
> =>> On Tue, 2008-04-08 at 15:27 -0400, Steven W. Orr wrote:
> =>> > On Tuesday, Apr 8th 2008 at 13:39 -0000, quoth Les:
> =>> > 
> =>> > =>On Tue, 2008-04-08 at 09:39 -0600, Robin Laing wrote:
> =>> > =>> max bianco wrote:
> =>> > =>> > I want to learn C and I know there are quite a few programmers on
> =>> > this
> =>> > =>> > list.  I am looking for a couple of good books on learning C. I am
> =>> > not
> =>> > =>> > exactly a beginner but I am no expert and i would like to start
> =>> > going
> =>> > =>> > over everything from scratch. 
> =>> > One thing I've noticed over the years is that the majority of C coders out
> =>> > there, no matter how good they are, never really master the ability to
> =>> > composed and decompose complex declarations and references. I don't say
> =>> > this in a perjorative fashion, but I see it a lot and it's important to be
> =>> > able to distinguish between an array of pointers to integers and a pointer
> =>> > to an array of integers, i.e.,
> =>> > 
> =>> > int *foo[10];
> =>> > int (*foo)[10];
> =>> > 
> =>> > Going through K&R is standard, but this is a basic complaint I've had for
> =>> > a long time.
> =>> 
> =>> This comment reminded me of the fabulously useful little utility cdecl
> =>> (and its cousin c++decl) which translates between the English
> =>> description of a declaration in C (resp. C++) and the actual C (resp.
> =>> C++) code itself.
> 
> cdecl tells you what it is but it doesn't tell you how to do it.
> 
> Since I have a few and I'm feeling inspired, here are the quick and simple 
> rules for declarations and referencing.:
> * There are three operators. *, {} and ()
> * The () is the function operator and is not to be confused with the 
> parens used to alter precedence.
> * The * is pronounced "pointer which returns a BLANK".
> * The [] is pronounced "an array of BLANKS".
> * The () is pronounced "a function which returns a BLANK"
> * An array can not hold functions. It can however contain pointers to 
> functions.
> * A function can not return an array or a function. It can however return 
> a pointer to an array or a function.
> * The precedence of function and array operators are equal and associate 
> from left to right.
> * The precedence of pointer is lower than the precedence of functions or 
> arrays.
> 
>         High Precedence  () []  
>                     left -> right
>         Lower Precedence *
>                     left <- right
> 
> That's it. So something like
> 
> typedef void (*sighandler_t) (int);
> sighandler_t signal(int signum, sighandler_t handler);
> 
> now becomes easy peasy. "sighandler_t is a type which is a pointer to a 
> function which takes an int as an arg and returns void. Signal is a 
> function which takes an int and a sighandler_t as args and returns a sighandler_t. 
> 
> This is (more or less) equivalent:
> 
> void (*signal( int signum, void hdlr(int))(int)
> 
> Quiz for next Friday. What are these and what's the difference between 
> them:
> 
> int     (*(**p)[])(int)
> and
> int     *(*(**p)[])(int)
> 
> -- 
> Time flies like the wind. Fruit flies like a banana. Stranger things have  .0.
> happened but none stranger than this. Does your driver's license say Organ ..0
> Donor?Black holes are where God divided by zero. Listen to me! We are all- 000
> individuals! What if this weren't a hypothetical question?
> steveo at syslang.net
> 
I'll go out on a limb here and say:

int     (*(**p)[])(int)
This is a pointer to an array of pointers each of points to an array of
functions returning an int, and requiring an int for the argument.

int     *(*(**p)[])(int)
This is a pointer to an array of pointers each of which points to an
array of functions returning a pointer to an integer, and requiring an
integer as an argument.

However I would pillory anyone writing such code unless they could prove
the requirement that made it necessary.

And by the way, returns by reference are common even in languages where
people believe they return the whole functions or results.  Doing
otherwise is just too slow given the construction of Von Neuman or
Harvard Architectures, as well as increasing stack memory demands.
Should one create a CAPP architecture machine it is possible to return
by processor reference which then would run the requisite function when
alerted, but I do not know of anyone who currently is fully utilizing
such CAPP architecture.  But I haven't looked lately either.

There have been rumors of fully parallel Lisp machines, with similar
attributes as CAPP, but I don't know of any real world uses for that
either.

Regards,
Les H




More information about the users mailing list