Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > typedef function pointer

Reply
Thread Tools

typedef function pointer

 
 
Cancerbero
Guest
Posts: n/a
 
      09-12-2004
Hi (first, excuse me for my bad english)

As I know, the semantics for typedef is:

typedef A B;

I think this makes B a synonym of A, where A is an existing data type. Is
that right?

Based on the previous definition of typedef, I can't understand the next:

typedef int (*TypeFunc) (int, int);

I think it's declaring a new type called TypeFunc. The objects of that
type are functions returning int and accepting two integer parameters.
But I can't understand the semantic of the last expresion. Based on the
first definition, the last should be:

typedef int (*) (int, int) TypeFunc;
/* first the existing datatype (pointer to function) and then the new
identifier datatype. */

Well, as you can see, I really can't understand the logic of the
semantics of typedef....

Thanks

--
Sebastián Gurin (Cancerbero)
cancerbero_sgx AT users.sourceforge.net

 
Reply With Quote
 
 
 
 
Jens.Toerring@physik.fu-berlin.de
Guest
Posts: n/a
 
      09-13-2004
Cancerbero <(E-Mail Removed)> wrote:
> As I know, the semantics for typedef is:


> typedef A B;


> I think this makes B a synonym of A, where A is an existing data type. Is
> that right?


Only in the most simple cases, so not really

> Based on the previous definition of typedef, I can't understand the next:


> typedef int (*TypeFunc) (int, int);


> I think it's declaring a new type called TypeFunc. The objects of that
> type are functions returning int and accepting two integer parameters.


That's correct if you replace 'functions' by 'pointers to functions'.
And it defines just a new identifier for a type, not a new type (because
'pointer to function returning int and taking two int arguments' isn't
a new type, all you do is creating a new name for it).

> But I can't understand the semantic of the last expresion. Based on the
> first definition, the last should be:


> typedef int (*) (int, int) TypeFunc;
> /* first the existing datatype (pointer to function) and then the new
> identifier datatype. */


But your first definition was too restrictive. It is as if you were
saying that a definition of a variable 'v' of type A always has the
form

A v;

But while that holds in some cases, it doesn't cover cases like a
definition of a function pointer, which you have to define like this

int ( * func_ptr ) ( int, int );

making 'func_ptr' a pointer to a function returning int and taking
two int arguments.

Now, if you compare that to the typedef you are worried about

typedef int ( * TypeFunc ) ( int, int );

you immediately see that a better description of the syntax of typedef
is that the new name you want to typedef goes in the place where in a
variable definition with that type the name of the variable would appear.

Another example would be a typedef for an array type, e.g. an array
of 10 ints. You would define such an array 'x' as

int x[ 10 ];

so, consequently, the typedef for an array of 10 ints must look
like this:

typedef int arr_of_ten_ints[ 10 ];

Regards, Jens
--
\ Jens Thoms Toerring ___ http://www.velocityreviews.com/forums/(E-Mail Removed)-berlin.de
\__________________________ http://www.toerring.de
 
Reply With Quote
 
 
 
 
Keith Thompson
Guest
Posts: n/a
 
      09-13-2004
Cancerbero <(E-Mail Removed)> writes:
> Hi (first, excuse me for my bad english)
>
> As I know, the semantics for typedef is:
>
> typedef A B;
>
> I think this makes B a synonym of A, where A is an existing data type. Is
> that right?


That's the syntax, not the semantics. "Syntax" refers to the way a
construct is written in C source; "semantics" refers to what it means.
(And actually that's not the syntax of a typedef, except in the
simplest cases.)

As Jens points out, it's like saying that the syntax of an object
declaration is
A v;
where v is the object name and A is the type. But if you wnat v
to be an array of 20 ints, the declaration is
int v[20];
which doesn't fit the simple "A v;" syntax.

But yes, "typedef A B;" makes B a synonym of A. That's the semantics.

> Based on the previous definition of typedef, I can't understand the next:
>
> typedef int (*TypeFunc) (int, int);


Syntactically, "typedef" is treated as a storage-class specifier, like
"extern", "static", "auto", or "register". It really isn't one (it
doesn't specify any kind of storage class), but it turned out to be
convenient to define the syntax that way (though one could argue that
it's not really all that convenient after all). So if you can
understand that

extern int (*Typefunc) (int, int);

declares an external pointer object called "Typefunc", that points
to a function taking to int arguments and returning it, then you can
understand that

typedef int (*Typefunc) (int, int);

declares a type name called "Typefunc", that refers to a pointer to a
function taking to int arguments and returning it.

Now it's just a matter of understanding C's declaration syntax.
Unfortunately, that's a non-trivial task.

The basic principle is that the declaration of an entity mirrors the
use of that entity. For example:
int *a;
declares a as a pointer to int. You can also think of it as declaring
that "*a" is an int.

Dropping the extern/typedef and changing the name, consider:
int (*foo) (int, int);
Back off a bit and look at the declaration as a whole. It says that
(*foo) (int, int)
will yield an int value. It looks like a function call, so the stuff
before the arguments
(int, int)
has to denote a function, so
(*foo)
denotes a function, so
foo
has to be a pointer to a function. We've already seen that the
function takes two int arguments, and that it returns int, so we can
conclude that
int (*foo) (int, int);
declares foo as a pointer object, specifically as a pointer to a
function taking two int arguments and returning int.

Add "extern", and it declares foo as an extern object of the same type.

Add "typedef" instead of "extern", and it declares foo as a type name
for the same type.

--
Keith Thompson (The_Other_Keith) http://www.velocityreviews.com/forums/(E-Mail Removed) <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this.
 
Reply With Quote
 
John Bode
Guest
Posts: n/a
 
      09-13-2004
Cancerbero <(E-Mail Removed)> wrote in message news:<pan.2004.09.10.12.03.02.460720.3248@montevid eo.com.uy>...
> Hi (first, excuse me for my bad english)
>
> As I know, the semantics for typedef is:
>
> typedef A B;
>
> I think this makes B a synonym of A, where A is an existing data type. Is
> that right?
>


Almost, but not quite. It works when talking about simple types and
identifiers, but breaks down for cases like what you describe below.

You need to read up on the concept of *declarators*, since they're
unique to C (and C++, and any other language directly derived from C).
The declarator introduces the name being declared and supplies
additional type information. For example, given the declaration

int *a[10];

the storage class is 'auto' (default), the type specifier is 'int',
the declarator is '*a[10]', and the identifier is 'a'. The type of
'a' is "10-element array of pointer to int"; the int-ness of 'a' is
specified through the type specifier, but the pointer-ness and
array-ness are specified through the declarator (incidentally, this is
why statements like "char* a, b;" don't work the way people think they
should; the '*' is associated with the identifier 'a', *not* the type
specifier 'char').

This is because C was designed with a "declaration mimics use"
paradigm. When you reference an item in an array, you use a subscript
operator []. When you dereference a pointer, you use the dereference
operator *. IOW, to get the int value pointed to by the 3rd array
element, you use the expression

*a[2];

which evaluates to an int type. So the idea was to make the
declaration of 'a' look the same as a reference to 'a' in the code. I
know this seemed like a good idea at the time, but in truth it makes
some operations harder than they need to be, and some declarations can
get obnoxiously difficult to write (which is where typedefs come in
handy). I've been programming in C for almost 15 years, and I didn't
*really* understand the concept until fairly recently.

What the typedef storage class does is make the *identifier* within
the declarator a synonym for an existing type. Going with the example
above, 'a' is a 10-element array of pointer to int. So the statement

typedef int *a[10];

creates a synonym for the existing type "10-element array of pointer
to int" and associates it with the identifier 'a'.

> Based on the previous definition of typedef, I can't understand the next:
>
> typedef int (*TypeFunc) (int, int);
>
> I think it's declaring a new type called TypeFunc. The objects of that
> type are functions returning int and accepting two integer parameters.
> But I can't understand the semantic of the last expresion. Based on the
> first definition, the last should be:
>
> typedef int (*) (int, int) TypeFunc;
> /* first the existing datatype (pointer to function) and then the new
> identifier datatype. */
>


Reference what I said above. The *declarator* is (*TypeFunc) (int,
int), which says that the *identifier* TypeFunc is a pointer to a
function taking two int parameters. TypeFunc becomes the typedef
name.

> Well, as you can see, I really can't understand the logic of the
> semantics of typedef....
>
> Thanks

 
Reply With Quote
 
Derrick Coetzee
Guest
Posts: n/a
 
      09-13-2004
Cancerbero wrote:
> Based on the previous definition of typedef, I can't understand the next:
>
> typedef int (*TypeFunc) (int, int);


This is one of the essential shortcomings of C - its declaration syntax,
especially for functions, mixes a variety of elements in a confusing
order. The goal, to make function type declarations resemble function
invocations, is for many people a confusion rather than an aid. You can
do much much worse, when you start talking about functions taking or
returning function pointers, or start worrying about where the * or &
goes when qualifiers abound.

In SPECS, an alternate C++ syntax designed by Damian Conway, your
typedef would look like this:

type TypeFunc : ^((int, int) -> int);

The type operator ^ means "pointer to", while X -> Y means "a function
taking X as an argument and returning Y." This is quite a bit closer to
what you suggested, and keeps the type info separate from the new
identifier. See Conway's paper for more:

http://www.csse.monash.edu.au/~damia...tProposal.html

--
Derrick Coetzee
I grant this newsgroup posting into the public domain. I disclaim all
express or implied warranty and all liability. I am not a professional.
 
Reply With Quote
 
Joona I Palaste
Guest
Posts: n/a
 
      09-14-2004
Derrick Coetzee <(E-Mail Removed)> scribbled the following:
> Cancerbero wrote:
>> Based on the previous definition of typedef, I can't understand the next:
>>
>> typedef int (*TypeFunc) (int, int);


> This is one of the essential shortcomings of C - its declaration syntax,
> especially for functions, mixes a variety of elements in a confusing
> order. The goal, to make function type declarations resemble function
> invocations, is for many people a confusion rather than an aid. You can
> do much much worse, when you start talking about functions taking or
> returning function pointers, or start worrying about where the * or &
> goes when qualifiers abound.


> In SPECS, an alternate C++ syntax designed by Damian Conway, your
> typedef would look like this:


> type TypeFunc : ^((int, int) -> int);


> The type operator ^ means "pointer to", while X -> Y means "a function
> taking X as an argument and returning Y." This is quite a bit closer to
> what you suggested, and keeps the type info separate from the new
> identifier. See Conway's paper for more:


> http://www.csse.monash.edu.au/~damia...tProposal.html


That looks strangely like Haskell syntax. Perhaps later we will be
seeing typedefs like this:

type TypeFunc: ^(((int, int) -> int) -> (int -> int));

meaning "pointer to a function, which takes a function taking an
(int, int) and returning int, an returns a function taking an int
and returning int".
This is not currently possible in either C or C++ because they can't
manufacture new functions at run-time but it would be nice in some
new mixed-paradigm language.

--
/-- Joona Palaste ((E-Mail Removed)) ------------- Finland --------\
\-- http://www.helsinki.fi/~palaste --------------------- rules! --------/
"'I' is the most beautiful word in the world."
- John Nordberg
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
CRTP-problem: How can the base class typedef a derived class' typedef? oor C++ 0 05-20-2008 12:39 PM
About typedef -- define the function pointer or define function model? robin liu C Programming 3 04-21-2006 03:26 PM
diffrence between "function pointer" and "pointer to a function" murgan C Programming 6 12-21-2005 06:01 AM
pointer to member function and pointer to constant member function Fraser Ross C++ 4 08-14-2004 06:00 PM
function pointer and member function pointer question glen stark C++ 2 10-10-2003 01:41 PM



Advertisments