function pointers as function parameters

Discussion in 'C Programming' started by Marlene Stebbins, May 2, 2005.

  1. I am experimenting with function pointers. Unfortunately, my C book has
    nothing on function pointers as function parameters. I want to pass a
    pointer to ff() to f() with the result that f() prints the return value
    of ff(). The code below seems to work, but I would appreciate your
    comments. Have I got it right? Does the function name "decay" to a pointer?


    #include <stdio.h>
    /* declares a function which takes an argument
    that is a pointer to a function returning an int */
    void f(int (*fptr)());
    /* function returning an int */
    int ff(void);

    int main(void)
    {
    f(ff); /* pass the address of ff to f */

    return 0;
    }

    void f(int (*fptr)())
    {
    int a;
    a = (*fptr)(); /* deref the func pointer */
    printf("%d\n", a);
    return;
    }

    int ff(void)
    {
    return 2345;
    }
    Marlene Stebbins, May 2, 2005
    #1
    1. Advertising

  2. Marlene Stebbins

    Eric Sosman Guest

    Marlene Stebbins wrote:
    > I am experimenting with function pointers. Unfortunately, my C book has
    > nothing on function pointers as function parameters. I want to pass a
    > pointer to ff() to f() with the result that f() prints the return value
    > of ff(). The code below seems to work, but I would appreciate your
    > comments. Have I got it right? Does the function name "decay" to a pointer?


    It might be simpler to say that the function name "is"
    a pointer to the function, since there is no context in
    which it does anything other than "decay."

    Your code is correct (as far as I can see), but there
    are a few opportunities for stylistic improvement:

    > #include <stdio.h>
    > /* declares a function which takes an argument
    > that is a pointer to a function returning an int */
    > void f(int (*fptr)());


    You know more about the pointed-to function than the
    type of its returned value: specifically, you know that
    it takes no arguments. (How do you know this? Because
    you supply no arguments when you call it.) On the general
    principle that it's best to tell the compiler everything
    you know, write the declaration as

    void f(int (*fptr)(void));

    This way, the compiler will protest if you inadvertently
    try to call the pointed-to function with arguments. If
    you do in fact want to pass arguments, say so:

    void f2(int (*fptr)(double, int, const char*));

    > /* function returning an int */
    > int ff(void);
    >
    > int main(void)
    > {
    > f(ff); /* pass the address of ff to f */


    Here's where ff "decays."

    > return 0;
    > }
    >
    > void f(int (*fptr)())


    If you've provided a prototype as suggested above,
    you should also do so here.

    > {
    > int a;
    > a = (*fptr)(); /* deref the func pointer */


    This can also be written `a = fptr();' without the
    parentheses and the asterisk. Some people prefer to write
    the call as you've done it, saying that it draws attention
    to the fact that a function pointer variable (rather than
    a function identifier) is being used. I personally don't
    buy that argument, noting that

    (*printf)("Hello, world!\n");

    is equally legitimate and (IMHO) equally silly. However,
    de gustibus non disputandum est (Latin for "There's just
    no arguing with Gus").

    > printf("%d\n", a);
    > return;
    > }
    >
    > int ff(void)
    > {
    > return 2345;
    > }


    --
    Eric Sosman, May 2, 2005
    #2
    1. Advertising

  3. Marlene Stebbins

    pete Guest

    Eric Sosman wrote:
    >
    > Marlene Stebbins wrote:
    > > I am experimenting with function pointers.
    > > Unfortunately, my C book has
    > > nothing on function pointers as function parameters.
    > > I want to pass a
    > > pointer to ff() to f() with the result that f()
    > > prints the return value
    > > of ff(). The code below seems to work, but I would appreciate your
    > > comments. Have I got it right?
    > > Does the function name "decay" to a pointer?

    >
    > It might be simpler to say that the function name "is"
    > a pointer to the function, since there is no context in
    > which it does anything other than "decay."


    The function name remains an expression of a function type
    when it is an operand of the address operator.
    You can force a non macro invocation of a standard library
    function by calling it like
    (&putchar)('\n');
    which wouldn't make sense if putchar were a pointer.
    If a function name were a pointer expression,
    then it would be a valid operand of the sizeof operator.
    For those two reasons,
    I would not say that a function name is a pointer.

    --
    pete
    pete, May 2, 2005
    #3
  4. Marlene Stebbins wrote on 02/05/05 :
    > #include <stdio.h>
    > /* declares a function which takes an argument
    > that is a pointer to a function returning an int */
    > void f(int (*fptr)());
    > /* function returning an int */
    > int ff(void);
    >
    > int main(void)
    > {
    > f(ff); /* pass the address of ff to f */
    >
    > return 0;
    > }
    >
    > void f(int (*fptr)())
    > {
    > int a;
    > a = (*fptr)(); /* deref the func pointer */
    > printf("%d\n", a);
    > return;
    > }
    >
    > int ff(void)
    > {
    > return 2345;
    > }


    You've got it (jist add 'void' into the () and it's all fine). Now, try
    the Simple Way:

    #include <stdio.h>

    typedef int F (void);

    static int ff (void)
    {
    return 2345;
    }

    static void f (F * pf)
    {
    /* deref the func pointer */
    int a = pf ();

    printf ("%d\n", a);
    return;
    }

    int main (void)
    {
    /* pass the address of ff to f */
    f (ff);

    return 0;
    }

    --
    Emmanuel
    The C-FAQ: http://www.eskimo.com/~scs/C-faq/faq.html
    The C-library: http://www.dinkumware.com/refxc.html

    "Clearly your code does not meet the original spec."
    "You are sentenced to 30 lashes with a wet noodle."
    -- Jerry Coffin in a.l.c.c++
    Emmanuel Delahaye, May 2, 2005
    #4
  5. Eric Sosman <> writes:
    > Marlene Stebbins wrote:
    >> I am experimenting with function pointers. Unfortunately, my C book has
    >> nothing on function pointers as function parameters. I want to pass a
    >> pointer to ff() to f() with the result that f() prints the return value
    >> of ff(). The code below seems to work, but I would appreciate your
    >> comments. Have I got it right? Does the function name "decay" to a pointer?

    >
    > It might be simpler to say that the function name "is"
    > a pointer to the function, since there is no context in
    > which it does anything other than "decay."


    Almost. A function name decays (is implicitly converted) to a pointer
    in most contexts. The exceptions are when it's the operand of a unary "&"
    (&ff yields a pointer-to-function, not a pointer-to-pointer-to-function),
    and when it's the operand of sizeof (sizeof ff is illegal; if it
    decayed in that context it would yield the size of a function
    pointer).

    [snip]
    > This can also be written `a = fptr();' without the
    > parentheses and the asterisk. Some people prefer to write
    > the call as you've done it, saying that it draws attention
    > to the fact that a function pointer variable (rather than
    > a function identifier) is being used. I personally don't
    > buy that argument, noting that
    >
    > (*printf)("Hello, world!\n");
    >
    > is equally legitimate and (IMHO) equally silly. However,
    > de gustibus non disputandum est (Latin for "There's just
    > no arguing with Gus").


    Note that
    (*printf)("Hello, world!\n");
    isn't exactly equivalent to
    printf("Hello, world!\n");
    since the latter could invoke a macro. That's a special rule for
    functions declared in standard headers. But if you want to avoid the
    macro and call the actual function, you can just use parentheses:

    (printf)("Hello, world!\n");

    Hmm. Actually, since printf() takes a variable number of arguments,
    implementing it as a macro is not possible in C90; I'm not sure
    whether it's possible in C99. But I digress.

    --
    Keith Thompson (The_Other_Keith) <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.
    Keith Thompson, May 2, 2005
    #5
  6. On Mon, 02 May 2005 18:59:12 +0000, pete wrote:

    > Eric Sosman wrote:
    >>
    >> Marlene Stebbins wrote:
    >> > I am experimenting with function pointers.
    >> > Unfortunately, my C book has
    >> > nothing on function pointers as function parameters.
    >> > I want to pass a
    >> > pointer to ff() to f() with the result that f()
    >> > prints the return value
    >> > of ff(). The code below seems to work, but I would appreciate your
    >> > comments. Have I got it right?
    >> > Does the function name "decay" to a pointer?

    >>
    >> It might be simpler to say that the function name "is"
    >> a pointer to the function, since there is no context in
    >> which it does anything other than "decay."

    >
    > The function name remains an expression of a function type
    > when it is an operand of the address operator.
    > You can force a non macro invocation of a standard library
    > function by calling it like
    > (&putchar)('\n');


    That's true although in practice it tends to be written as

    (putchar)('\n');

    > which wouldn't make sense if putchar were a pointer.


    But, yes, your form makes this point.

    > If a function name were a pointer expression,
    > then it would be a valid operand of the sizeof operator.
    > For those two reasons,
    > I would not say that a function name is a pointer.


    It is a very similar argument to that for array names. Array names have
    array type but in many cases an array "value" is given as a pointer to the
    array's first element, so in those cases it appears to be a pointer. But
    it isn't and as with functions &array and sizeof array show its true
    nature.

    Lawrence
    Lawrence Kirby, May 3, 2005
    #6
  7. Marlene Stebbins

    pete Guest

    Lawrence Kirby wrote:
    >
    > On Mon, 02 May 2005 18:59:12 +0000, pete wrote:
    >
    > > Eric Sosman wrote:


    > >> It might be simpler to say that the function name "is"
    > >> a pointer to the function, since there is no context in
    > >> which it does anything other than "decay."

    > >
    > > The function name remains an expression of a function type
    > > when it is an operand of the address operator.
    > > You can force a non macro invocation of a standard library
    > > function by calling it like
    > > (&putchar)('\n');

    >
    > That's true although in practice it tends to be written as
    >
    > (putchar)('\n');
    >
    > > which wouldn't make sense if putchar were a pointer.

    >
    > But, yes, your form makes this point.
    >
    > > If a function name were a pointer expression,
    > > then it would be a valid operand of the sizeof operator.
    > > For those two reasons,
    > > I would not say that a function name is a pointer.

    >
    > It is a very similar argument to that for array names.
    > Array names have array type but in many cases an array "value"
    > is given as a pointer to the array's first element,
    > so in those cases it appears to be a pointer.
    > But it isn't and as with functions &array
    > and sizeof array show its true nature.


    I would agree with Eric Sosman's statement to the extent
    that the only use of a value of an expression of a function type,
    is that a pointer can be derived from it.

    What constitutes the value of an array type, is more complicated.
    The value of an array type (even an incomplete array type)
    can be converted to a pointer.
    The value of an array type can initialize an array.
    char array[] = "";
    The value of an array type structure member,
    is a byte by byte copy when the structure
    is an operand of the assignment operator.

    --
    pete
    pete, May 3, 2005
    #7
  8. Jonathan Bartlett, May 3, 2005
    #8
  9. In article <>, Keith Thompson <> writes:
    > Eric Sosman <> writes:
    > >
    > > It might be simpler to say that the function name "is"
    > > a pointer to the function, since there is no context in
    > > which it does anything other than "decay."

    >
    > Almost. A function name decays (is implicitly converted) to a pointer
    > in most contexts. The exceptions are when it's the operand of a unary "&"
    > (&ff yields a pointer-to-function, not a pointer-to-pointer-to-function),
    > and when it's the operand of sizeof (sizeof ff is illegal; if it
    > decayed in that context it would yield the size of a function
    > pointer).


    I was mulling over the hypothesis that the & and * operators, when
    applied to function names, simply did nothing, but your last example
    made me think of a possible counterexample. Is the following a
    strictly conforming expression?

    sizeof &main;

    Or, if you prefer the full-program version:

    #include <stdio.h>
    int main(void) {
    printf("%lu\n", (unsigned long) sizeof &main);
    return 0;
    }

    If it is, aside from that, are there any other cases where the & and
    * operators have any effect when applied to a function name?

    --
    Michael Wojcik

    "We are facing a dire shortage of clowns," said Erickson, also known as
    Jingles.
    Michael Wojcik, May 3, 2005
    #9
  10. Marlene Stebbins

    Eric Sosman Guest

    pete wrote:
    > Lawrence Kirby wrote:
    >
    >>On Mon, 02 May 2005 18:59:12 +0000, pete wrote:
    >>
    >>
    >>>Eric Sosman wrote:

    >
    >
    >>>> It might be simpler to say that the function name "is"
    >>>>a pointer to the function, since there is no context in
    >>>>which it does anything other than "decay."
    >>>
    >>>The function name remains an expression of a function type
    >>>when it is an operand of the address operator.
    >>>You can force a non macro invocation of a standard library
    >>>function by calling it like
    >>> (&putchar)('\n');

    >>
    >>That's true although in practice it tends to be written as
    >>
    >> (putchar)('\n');
    >>
    >>
    >>>which wouldn't make sense if putchar were a pointer.

    >>
    >>But, yes, your form makes this point.
    >>
    >>
    >>>If a function name were a pointer expression,
    >>>then it would be a valid operand of the sizeof operator.
    >>>For those two reasons,
    >>>I would not say that a function name is a pointer.

    >>
    >>It is a very similar argument to that for array names.
    >>Array names have array type but in many cases an array "value"
    >>is given as a pointer to the array's first element,
    >>so in those cases it appears to be a pointer.
    >>But it isn't and as with functions &array
    >>and sizeof array show its true nature.

    >
    >
    > I would agree with Eric Sosman's statement to the extent
    > that the only use of a value of an expression of a function type,
    > is that a pointer can be derived from it.


    Although it's flattering to learn that someone agrees with
    me, it is also a bit embarrassing -- because I have come to
    *dis*agree with myself ;-)

    I said there was no context in which a function identifier
    doesn't "decay" to a pointer to the function, but Keith
    Thompson has convinced me I was wrong. Specifically:

    - In the context `&func', the `func' part does not behave
    like a pointer-to-function. If it did, the entire
    expression would be pointer-to-pointer-to-function --
    but, strangely enough, both `func' and `&func' (and
    even `&&&&&&&func') are pointer-to-function.

    - In the context `sizeof func', the `func' part does not
    behave like a pointer-to-function. If it did, the
    expression would evaluate to the size of a function
    pointer, but in actuality the expression produces a
    diagnostic.

    The second point is debatable: since the context is not
    valid C at all, its odd behavior doesn't matter. One might
    equally well make arguments about the array-indexing operator
    in the context `[4]"Hello"'; interesting things might be said,
    but they'd have little to do with C. But even if one rejects
    the second point, the first seems unassailable: Keith is right
    and I was wrong, R-O-N-G, wrong.

    --
    Eric Sosman, May 3, 2005
    #10
  11. On Tue, 03 May 2005 10:57:05 -0400, Eric Sosman wrote:

    ....

    > I said there was no context in which a function identifier
    > doesn't "decay" to a pointer to the function, but Keith
    > Thompson has convinced me I was wrong. Specifically:
    >
    > - In the context `&func', the `func' part does not behave
    > like a pointer-to-function. If it did, the entire
    > expression would be pointer-to-pointer-to-function --
    > but, strangely enough, both `func' and `&func' (and
    > even `&&&&&&&func') are pointer-to-function.


    Using the && operator like this is a syntax error. But even
    (& &func) is invalid because unary & requires an lvalue or function
    designator as its operand, but it doesn't produce either as its result.

    Lawrence
    Lawrence Kirby, May 3, 2005
    #11
  12. Eric Sosman <> writes:
    [...]
    > Although it's flattering to learn that someone agrees with
    > me, it is also a bit embarrassing -- because I have come to
    > *dis*agree with myself ;-)
    >
    > I said there was no context in which a function identifier
    > doesn't "decay" to a pointer to the function, but Keith
    > Thompson has convinced me I was wrong. Specifically:
    >
    > - In the context `&func', the `func' part does not behave
    > like a pointer-to-function. If it did, the entire
    > expression would be pointer-to-pointer-to-function --
    > but, strangely enough, both `func' and `&func' (and
    > even `&&&&&&&func') are pointer-to-function.


    As Lawrence Kirby pointed out, this is illegal because the "maximal
    munch" rule turns this into three "&&" operators followed by an "&"
    operator; once you fix that, it's still illegal because &func isn't a
    lvalue. But you can have &func, func, *func, **func, *****func, and
    *&*&*&*&func.

    > - In the context `sizeof func', the `func' part does not
    > behave like a pointer-to-function. If it did, then
    > expression would evaluate to the size of a function
    > pointer, but in actuality the expression produces a
    > diagnostic.
    >
    > The second point is debatable: since the context is not
    > valid C at all, its odd behavior doesn't matter. One might
    > equally well make arguments about the array-indexing operator
    > in the context `[4]"Hello"'; interesting things might be said,
    > but they'd have little to do with C. But even if one rejects
    > the second point, the first seems unassailable: Keith is right
    > and I was wrong, R-O-N-G, wrong.


    I hate to force you to disagree with yourself even further, but here's
    what the standard says:

    C99 6.3.2.1p4:

    A function designator is an expression that has function
    type. Except when it is the operand of the sizeof operator(54) or
    the unary & operator, a function designator with type "function
    returning type" is converted to an expression that has type
    "pointer to function returning type".

    And footnote (54):

    Because this conversion does not occur, the operand of the sizeof
    operator remains a function designator and violates the constraint
    in 6.5.3.4.

    6.5.3.4p1 says:

    Constraints

    The sizeof operator shall not be applied to an expression that has
    function type or an incomplete type, to the parenthesized name of
    such a type, or to an expression that designates a bit-field
    member.

    It seems a little convoluted to make an exception to the rule for the
    operand of a sizeof operator, only to make it a constraint violation
    in a different section of the standard, but I think this is actually
    the most straightforward way to do it. The rule is similar to the
    rule for arrays, except that it makes sense to apply sizeof to an
    array value.

    [4]"Hello", on the other hand, is a syntax error, not a constraint
    violation. (And as you know, 4["Hello"] is perfectly legal.)

    --
    Keith Thompson (The_Other_Keith) <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.
    Keith Thompson, May 3, 2005
    #12
  13. Marlene Stebbins

    pete Guest

    Michael Wojcik wrote:

    > sizeof &main;


    That's the size of a pointer.

    > If it is, aside from that, are there any other cases where the & and
    > * operators have any effect when applied to a function name?


    The * operator always converts the function type expression
    to a pointer, prior to operating on it.

    These are all valid function calls:

    (putchar)('\n');
    (&putchar)('\n');
    (*putchar)('\n');

    In the first one, the function type expression,
    is converted to a pointer, by the function call operator.

    The second one has no conversions.

    In the third one, the * operator converts the function type
    expression to a pointer, then operates on it,
    the result is an expression of function type
    which is converted to a pointer by the function call operator.

    --
    pete
    pete, May 4, 2005
    #13
  14. Marlene Stebbins

    pete Guest

    Eric Sosman wrote:
    >
    > pete wrote:
    > > Lawrence Kirby wrote:
    > >
    > >>On Mon, 02 May 2005 18:59:12 +0000, pete wrote:
    > >>
    > >>
    > >>>Eric Sosman wrote:

    > >
    > >
    > >>>> It might be simpler to say that the function name "is"
    > >>>>a pointer to the function, since there is no context in
    > >>>>which it does anything other than "decay."
    > >>>
    > >>>The function name remains an expression of a function type
    > >>>when it is an operand of the address operator.
    > >>>You can force a non macro invocation of a standard library
    > >>>function by calling it like
    > >>> (&putchar)('\n');
    > >>
    > >>That's true although in practice it tends to be written as
    > >>
    > >> (putchar)('\n');
    > >>
    > >>
    > >>>which wouldn't make sense if putchar were a pointer.
    > >>
    > >>But, yes, your form makes this point.
    > >>
    > >>
    > >>>If a function name were a pointer expression,
    > >>>then it would be a valid operand of the sizeof operator.
    > >>>For those two reasons,
    > >>>I would not say that a function name is a pointer.
    > >>
    > >>It is a very similar argument to that for array names.
    > >>Array names have array type but in many cases an array "value"
    > >>is given as a pointer to the array's first element,
    > >>so in those cases it appears to be a pointer.
    > >>But it isn't and as with functions &array
    > >>and sizeof array show its true nature.

    > >
    > >
    > > I would agree with Eric Sosman's statement to the extent
    > > that the only use of a value of an expression of a function type,
    > > is that a pointer can be derived from it.

    >
    > Although it's flattering to learn that someone agrees with
    > me, it is also a bit embarrassing -- because I have come to
    > *dis*agree with myself ;-)
    >
    > I said there was no context in which a function identifier
    > doesn't "decay" to a pointer to the function, but Keith
    > Thompson has convinced me I was wrong. Specifically:
    >
    > - In the context `&func', the `func' part does not behave
    > like a pointer-to-function. If it did, the entire
    > expression would be pointer-to-pointer-to-function --
    > but, strangely enough, both `func' and `&func' (and
    > even `&&&&&&&func') are pointer-to-function.
    >
    > - In the context `sizeof func', the `func' part does not
    > behave like a pointer-to-function. If it did, the
    > expression would evaluate to the size of a function
    > pointer, but in actuality the expression produces a
    > diagnostic.
    >
    > The second point is debatable: since the context is not
    > valid C at all, its odd behavior doesn't matter.


    The fact that the function name is not a pointer, is the
    reason why the function name is not a valid operand of sizeof.
    Function pointers are object types and valid operands of sizeof.
    So, if the point is whether or not function names are pointers,
    then the sizeof issue is relevant.

    > One might
    > equally well make arguments about the array-indexing operator
    > in the context `[4]"Hello"'; interesting things might be said,
    > but they'd have little to do with C.


    The array indexing operator converts the array name to a pointer,
    just as the * operator does with both array names and function names.

    --
    pete
    pete, May 4, 2005
    #14
  15. pete <> writes:
    > Michael Wojcik wrote:
    >
    >> sizeof &main;

    >
    > That's the size of a pointer.
    >
    >> If it is, aside from that, are there any other cases where the & and
    >> * operators have any effect when applied to a function name?

    >
    > The * operator always converts the function type expression
    > to a pointer, prior to operating on it.


    No, the * operator doesn't do any conversions. The conversion occurs
    before the * operator is invoked. Perhaps this is just a matter of
    terminology, but in my opinion saying that the operator converts its
    operand is misleading. The * operator expects a pointer operand; it
    gets one because the operand is already a pointer.

    Given
    int n;
    the expression *n is illegal. If the * operator had the ability to
    convert its operand to a pointer type, *n would be equivalent to n.
    You could argue, I suppose, that the * operator converts its operand
    only in certain circumstances, but I don't see any support for this
    idea in the standard.

    > These are all valid function calls:
    >
    > (putchar)('\n');
    > (&putchar)('\n');
    > (*putchar)('\n');
    >
    > In the first one, the function type expression,
    > is converted to a pointer, by the function call operator.


    The expression putchar is of function type. Since it's not the
    operand of a sizeof or "&" operator, it's implicitly converted to a
    pointer-to-function. The parenthesized expression is a no-op, used
    only for syntactic resolution. This pointer-to-function *then*
    becomes an operand of the function call operator; since the function
    call operator expects a pointer-to-function, no further conversion is
    necessary.

    > The second one has no conversions.


    Agreed.

    > In the third one, the * operator converts the function type
    > expression to a pointer, then operates on it,
    > the result is an expression of function type
    > which is converted to a pointer by the function call operator.


    The expression putchar is of function type. Since it's not the
    operand of a sizeof or "&" operator, it's implicitly converted to a
    pointer-to-function. The "*" operator expects, and gets, a pointer as
    its operand; it yields an lvalue designating the thing the pointer
    points to. In this case, the result is an lvalue designating the
    putchar function. This is, again, an expression of function type.
    Since this is also not the operand of a sizeof or "&" operator, it's
    again implicitly converted to a pointer-to-function type. The
    parentheses again have no semantic effect. The function call operator
    expects, and gets, a pointer-to-function as its operand.

    --
    Keith Thompson (The_Other_Keith) <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.
    Keith Thompson, May 4, 2005
    #15
  16. Marlene Stebbins

    pete Guest

    Keith Thompson wrote:
    >
    > pete <> writes:
    > > Michael Wojcik wrote:
    > >
    > >> sizeof &main;

    > >
    > > That's the size of a pointer.
    > >
    > >> If it is, aside from that,
    > >> are there any other cases where the & and
    > >> * operators have any effect when applied to a function name?

    > >
    > > The * operator always converts the function type expression
    > > to a pointer, prior to operating on it.

    >
    > No, the * operator doesn't do any conversions. The conversion occurs
    > before the * operator is invoked. Perhaps this is just a matter of
    > terminology, but in my opinion saying that the operator converts its
    > operand is misleading.


    N869
    6.3 Conversions
    [#1] Several operators convert operand values from one type
    to another automatically.

    --
    pete
    pete, May 4, 2005
    #16
  17. Marlene Stebbins

    pete Guest

    pete wrote:
    >
    > Keith Thompson wrote:
    > >
    > > pete <> writes:
    > > > Michael Wojcik wrote:
    > > >
    > > >> sizeof &main;
    > > >
    > > > That's the size of a pointer.
    > > >
    > > >> If it is, aside from that,
    > > >> are there any other cases where the & and
    > > >> * operators have any effect when applied to a function name?
    > > >
    > > > The * operator always converts the function type expression
    > > > to a pointer, prior to operating on it.

    > >
    > > No, the * operator doesn't do any conversions. The conversion occurs
    > > before the * operator is invoked. Perhaps this is just a matter of
    > > terminology, but in my opinion saying that the operator converts its
    > > operand is misleading.

    >
    > N869
    > 6.3 Conversions
    > [#1] Several operators convert operand values from one type
    > to another automatically.


    I think you're right. It would be accurate
    to say that not being the operand of & or sizeof,
    is what converts the function type expression to a pointer.

    --
    pete
    pete, May 4, 2005
    #17
  18. pete <> writes:
    > Keith Thompson wrote:

    [snip]
    >> No, the * operator doesn't do any conversions. The conversion occurs
    >> before the * operator is invoked. Perhaps this is just a matter of
    >> terminology, but in my opinion saying that the operator converts its
    >> operand is misleading.

    >
    > N869
    > 6.3 Conversions
    > [#1] Several operators convert operand values from one type
    > to another automatically.


    Hmm, that's an odd statement. I don't have access to my copy of the
    standard at the moment; I'll take a look at the context later tonight.
    Maybe it's refering to arithmetic promotions?

    --
    Keith Thompson (The_Other_Keith) <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.
    Keith Thompson, May 4, 2005
    #18
  19. Keith Thompson <> writes:
    > pete <> writes:
    >> Keith Thompson wrote:

    > [snip]
    >>> No, the * operator doesn't do any conversions. The conversion occurs
    >>> before the * operator is invoked. Perhaps this is just a matter of
    >>> terminology, but in my opinion saying that the operator converts its
    >>> operand is misleading.

    >>
    >> N869
    >> 6.3 Conversions
    >> [#1] Several operators convert operand values from one type
    >> to another automatically.

    >
    > Hmm, that's an odd statement. I don't have access to my copy of the
    > standard at the moment; I'll take a look at the context later tonight.
    > Maybe it's refering to arithmetic promotions?


    Yes, it's talking about the "usual arithmetic conversions".

    C99 6.3p1:

    Several operators convert operand values from one type to another
    automatically. This subclause specifies the result required from
    such an implicit conversion, as well as those that result from a
    cast operation (an explicit conversion). The list in 6.3.1.8
    summarizes the conversions performed by most ordinary operators;
    it is supplemented as required by the discussion of each operator
    in 6.5.

    6.3.1.8, "Usual arithmetic conversions", covers things like the "*"
    operator in 1.2 * 3 converting its right operand from int to double.
    IMHO it would make more sense to say that the right operand is
    converted to double because of the context in which it appears, not
    that it's converted by the operator, but that's the wording chosen in
    the standard.

    --
    Keith Thompson (The_Other_Keith) <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.
    Keith Thompson, May 4, 2005
    #19
  20. Marlene Stebbins

    pete Guest

    Keith Thompson wrote:
    >
    > Keith Thompson <> writes:
    > > pete <> writes:
    > >> Keith Thompson wrote:

    > > [snip]
    > >>> No, the * operator doesn't do any conversions. The conversion occurs
    > >>> before the * operator is invoked. Perhaps this is just a matter of
    > >>> terminology, but in my opinion saying that the operator converts its
    > >>> operand is misleading.
    > >>
    > >> N869
    > >> 6.3 Conversions
    > >> [#1] Several operators convert operand values from one type
    > >> to another automatically.

    > >
    > > Hmm, that's an odd statement. I don't have access to my copy of the
    > > standard at the moment; I'll take a look at the context later tonight.
    > > Maybe it's refering to arithmetic promotions?

    >
    > Yes, it's talking about the "usual arithmetic conversions".
    >
    > C99 6.3p1:
    >
    > Several operators convert operand values from one type to another
    > automatically. This subclause specifies the result required from
    > such an implicit conversion, as well as those that result from a
    > cast operation (an explicit conversion). The list in 6.3.1.8
    > summarizes the conversions performed by most ordinary operators;
    > it is supplemented as required by the discussion of each operator
    > in 6.5.
    >
    > 6.3.1.8, "Usual arithmetic conversions", covers things like the "*"
    > operator in 1.2 * 3 converting its right operand from int to double.
    > IMHO it would make more sense to say that the right operand is
    > converted to double because of the context in which it appears, not
    > that it's converted by the operator, but that's the wording chosen in
    > the standard.


    I had mistakenly interpreted the standard to mean
    that being the operand of operators other than sizeof or &,
    was the condition which caused conversion. That's close,
    because if a function name isn't the operand of sizeof or &,
    then it's usually the operand of some other operator,
    but not always.
    I can only think of two cases where a function name would be converted
    without being an operand:
    Initialization of a function pointer
    ptr = function_name;
    and a no op statement
    function_name;

    --
    pete
    pete, May 4, 2005
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Phil
    Replies:
    1
    Views:
    639
    llewelly
    Sep 16, 2003
  2. Peter Goddard

    void pointers & void function pointers

    Peter Goddard, May 16, 2005, in forum: C Programming
    Replies:
    3
    Views:
    505
    Peter Goddard
    May 16, 2005
  3. n2xssvv g02gfr12930

    Smart pointers and member function pointers

    n2xssvv g02gfr12930, Nov 26, 2005, in forum: C++
    Replies:
    3
    Views:
    461
    n2xssvv g02gfr12930
    Nov 27, 2005
  4. Dilip
    Replies:
    3
    Views:
    503
    Dilip
    Nov 6, 2006
  5. cerr

    pointers, pointers, pointers...

    cerr, Apr 7, 2011, in forum: C Programming
    Replies:
    12
    Views:
    652
Loading...

Share This Page