Question on Basic Function Syntax

Discussion in 'C++' started by Danny Gratzer, Apr 8, 2012.

  1. Hello,
    I have been reading my way through C++ Primer and I noticed that the
    function prototype for one of the functions resembled this

    class A{

    public:
    void f(const int& a) const;
    ....
    };

    what is the purpose of that second const following f's parameters?

    thanks in advance.
    Danny Gratzer, Apr 8, 2012
    #1
    1. Advertising

  2. Danny Gratzer

    Paul N Guest

    On Apr 8, 8:40 pm, Danny Gratzer <> wrote:
    > Hello,
    > I have been reading my way through C++ Primer and I noticed that the
    > function prototype for one of the functions resembled this
    >
    > class A{
    >
    > public:
    >           void f(const int& a) const;
    > ...
    >
    > };
    >
    > what is the purpose of that second const following f's parameters?
    >
    > thanks in advance.


    It means that calling the function doesn't alter the object that it is
    called on.
    Paul N, Apr 8, 2012
    #2
    1. Advertising

  3. Danny Gratzer

    Guest

    Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    On Sunday, April 8, 2012 2:56:35 PM UTC-5, (unknown) wrote:
    > 
    >
    > &quot;f() const;&quot;, defined inside a struct ( i.e. a &quot;class&quot; )
    > can't change the variables in the struct.
    >
    > I say &quot;struct&quot; because, to my mind, that's what it is, not a &quot;class&quot;.
    > </pre>


    Is there a proper name for something like that? also can any other qualifiers besides const be used like that?
    , Apr 8, 2012
    #3
  4. Danny Gratzer

    Guest

    Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    On Sunday, April 8, 2012 2:56:35 PM UTC-5, (unknown) wrote:
    > 
    >
    > &quot;f() const;&quot;, defined inside a struct ( i.e. a &quot;class&quot; )
    > can't change the variables in the struct.
    >
    > I say &quot;struct&quot; because, to my mind, that's what it is, not a &quot;class&quot;.
    > </pre>


    I see, are there any other modifiers that can be placed in that position besides const?
    , Apr 8, 2012
    #4
  5. Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    On 4/8/2012 4:04 PM, wrote:
    > On Sunday, April 8, 2012 2:56:35 PM UTC-5, (unknown) wrote:
    >> 
    >>
    >> &quot;f() const;&quot;, defined inside a struct ( i.e. a&quot;class&quot; )
    >> can't change the variables in the struct.
    >>
    >> I say&quot;struct&quot; because, to my mind, that's what it is, not a&quot;class&quot;.
    >> </pre>

    >
    > Is there a proper name for something like that? also can any other qualifiers besides const be used like that?


    It's a cv-qualifier. Other possibilities are "volatile" and "const
    volatile".

    V
    --
    I do not respond to top-posted replies, please don't ask
    Victor Bazarov, Apr 8, 2012
    #5
  6. Danny Gratzer

    Marc Guest

    Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    Victor Bazarov wrote:

    > On 4/8/2012 4:04 PM, wrote:
    >> On Sunday, April 8, 2012 2:56:35 PM UTC-5, (unknown) wrote:
    >>> 
    >>>
    >>> &quot;f() const;&quot;, defined inside a struct ( i.e. a&quot;class&quot; )
    >>> can't change the variables in the struct.
    >>>
    >>> I say&quot;struct&quot; because, to my mind, that's what it is, not a&quot;class&quot;.
    >>> </pre>

    >>
    >> Is there a proper name for something like that? also can any other qualifiers besides const be used like that?

    >
    > It's a cv-qualifier. Other possibilities are "volatile" and "const
    > volatile".


    In C++11, you can also put a ref-qualifier (& or &&) there, so it is
    even more similar to regular arguments of a function.
    Marc, Apr 8, 2012
    #6
  7. Danny Gratzer

    Rui Maciel Guest

    Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    wrote:

    > I see, are there any other modifiers that can be placed in that position
    > besides const?


    Yes, a member function may be declared as const and/or volatile.

    Just to provide you with some insight, in the C++ programming language
    member functions may be interpreted as being funcions which have an implicit
    parameter which takes a pointer to an object of a particular class. So,
    conceptually, in the following example both Foo::member_do() and
    function_do(Foo *) would be equivalent:

    <code>
    class Foo
    {
    public:
    void member_do() {};
    };

    void function_do(Foo *)
    {
    }
    </code>

    With this in mind, when you declare a member function as const, volatile or
    const volatile, you are declaring how that function accesses the pointer to
    an object of that class. So, tweaking the previous example, the following
    would also be equivalent:

    <code>
    class Foo
    {
    public:
    void member_do() const {};
    void member_do() volatile {};
    void member_do() const volatile {};
    };

    void function_do(const Foo *)
    {
    }

    void function_do(volatile Foo *)
    {
    }

    void function_do(const volatile Foo *)
    {
    }
    </code>


    Hope this helps,
    Rui Maciel
    Rui Maciel, Apr 8, 2012
    #7
  8. Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    On 08.04.2012 22:46, Victor Bazarov wrote:
    > On 4/8/2012 4:04 PM, wrote:
    >> On Sunday, April 8, 2012 2:56:35 PM UTC-5, (unknown) wrote:
    >>> 
    >>>
    >>> &quot;f() const;&quot;, defined inside a struct ( i.e.
    >>> a&quot;class&quot; )
    >>> can't change the variables in the struct.
    >>>
    >>> I say&quot;struct&quot; because, to my mind, that's what it is,
    >>> not a&quot;class&quot;.
    >>> </pre>

    >>
    >> Is there a proper name for something like that? also can any other
    >> qualifiers besides const be used like that?

    >
    > It's a cv-qualifier. Other possibilities are "volatile" and "const
    > volatile".


    And, as of C++11, the cv-qualifiers can be followed by ref-qualifiers,
    "&" and "&&".

    Which serve a similar purpose, in restricting use of the methods.

    C++11 §5.5/6
    "In a .* expression whose object expression is an rvalue, the program is
    ill-formed if the second operand is a pointer to member function with
    ref-qualifier &. In a .* expression whose object expression is an
    lvalue, the program is ill-formed if the second operand is a pointer to
    member function with ref-qualifier &&."

    C++11 §13.3.1/4
    "For non-static member functions, the type of the implicit object
    parameter is
    — “lvalue reference to cv X†for functions declared without a
    ref-qualifier or with the & ref-qualifier
    — “rvalue reference to cv X†for functions declared with the &&
    ref-qualifier"


    C++11 §13.3.1/5
    "For non-static member functions declared without a ref-qualifier, an
    additional rule applies:
    — even if the implicit object parameter is not const-qualified, an
    rvalue can be bound to the parameter as long as in all other respects
    the argument can be converted to the type of the implicit object parameter."

    Essentially, the last para means that the ordinary
    freely-call-methods-on-temporaries rule is disabled for methods with
    ref-qualifiers. The two first paras then mean that a "&" method can only
    be called on an rvalue, and that a "&&" method can only be called on an
    lvalue. Keeping in mind that rvalue and lvalue refer to expressions, not
    objects, and also modulo the more precise C++11 terminology which I
    don't master yet.

    Cheers,

    - Alf
    Alf P. Steinbach, Apr 8, 2012
    #8
  9. Paul N <> wrote:
    > It means that calling the function doesn't alter the object that it is
    > called on.


    Actually it doesn't.

    What it means is that if you have a const object (or const reference/pointer
    to such a type) of that class type, you can call said function.

    *In principle* said function shouldn't modify the object, or else the
    semantics of constness get broken, but in practice there are situations
    where it's actually something that can happen, and there's even a keyword
    to achieve that (namely "mutable").

    Anyways, the key here is that you should *always* declare your members
    functions as 'const' unless they really need to modify the object. That's
    because it allows calling those functions when the object itself is const.
    Juha Nieminen, Apr 9, 2012
    #9
  10. Danny Gratzer

    Bo Persson Guest

    Paul N skrev 2012-04-08 21:42:
    > On Apr 8, 8:40 pm, Danny Gratzer<> wrote:
    >> Hello,
    >> I have been reading my way through C++ Primer and I noticed that the
    >> function prototype for one of the functions resembled this
    >>
    >> class A{
    >>
    >> public:
    >> void f(const int& a) const;
    >> ...
    >>
    >> };
    >>
    >> what is the purpose of that second const following f's parameters?
    >>
    >> thanks in advance.

    >
    > It means that calling the function doesn't alter the object that it is
    > called on.


    Which also allows you to call the function for constant objects.


    Bo Persson
    Bo Persson, Apr 9, 2012
    #10
  11. Danny Gratzer

    Guest

    Re: "f() const;", defined inside a struct ( i.e. a "class" ). 

    On Sunday, April 8, 2012 8:56:35 PM UTC+1, (unknown) wrote:
    > 
    >
    > &quot;f() const;&quot;, defined inside a struct ( i.e. a &quot;class&quot; )
    > can't change the variables in the struct.
    >
    > I say &quot;struct&quot; because, to my mind, that's what it is, not a &quot;class&quot;.
    > </pre>


    it's a C++ class
    , Apr 10, 2012
    #11
  12. Danny Gratzer

    Jorgen Grahn Guest

    On Mon, 2012-04-09, Juha Nieminen wrote:
    > Paul N <> wrote:
    >> It means that calling the function doesn't alter the object that it is
    >> called on.

    >
    > Actually it doesn't.
    >
    > What it means is that if you have a const object (or const reference/pointer
    > to such a type) of that class type, you can call said function.
    >
    > *In principle* said function shouldn't modify the object, or else the
    > semantics of constness get broken, but in practice there are situations
    > where it's actually something that can happen, and there's even a keyword
    > to achieve that (namely "mutable").


    Shouldn't modify the object /via the 'this' pointer/ to be more
    precise. This is ok, for example:

    struct Foo {
    void bar(Foo& f) const { mess_up(f); }
    };

    Foo foo;
    foo.bar(foo); // modifies foo

    But his book should tell him all of this.

    /Jorgen

    --
    // Jorgen Grahn <grahn@ Oo o. . .
    \X/ snipabacken.se> O o .
    Jorgen Grahn, Apr 10, 2012
    #12
  13. Jorgen Grahn <> wrote:
    > Shouldn't modify the object /via the 'this' pointer/ to be more
    > precise.


    As said, the 'mutable' keyword allows modifications of the object pointed
    by 'this' even if it's const. (While there are other ways to bypass constness,
    'mutable' is by far the cleanest and most self-documenting way of doing it.
    Basically you are telling at a language level that "this member variable can
    be modified by const methods.")

    One concrete example of a valid use for 'mutable' is a non-intrusive
    smart pointer that uses the double-linking strategy (instead of using a
    reference counter): When such a smart pointer is copied/assigned, the
    original (which is passed as const reference to the copy constructor or
    copy assignment operator) is not modified in its behavior, but internally
    its "linded list" pointers need to be modified, and marking them as 'mutable'
    is the cleanest way of doing that. (The external behavior of the pointer still
    retains its constness, so this is a valid situation to use 'mutable'.)
    Juha Nieminen, Apr 10, 2012
    #13
  14. Danny Gratzer

    Jorgen Grahn Guest

    On Tue, 2012-04-10, Juha Nieminen wrote:
    > Jorgen Grahn <> wrote:
    >> Shouldn't modify the object /via the 'this' pointer/ to be more
    >> precise.

    >
    > As said, the 'mutable' keyword allows modifications of the object pointed
    > by 'this' even if it's const.

    ....

    Uh, we are talking about different things. I was unclear, but it
    should have gone roughly:

    Someone: FOO doesn't modify the object.
    You: Explained 'mutable' as an exception.
    Me: Explained that also, the "doesn't modify" doesn't
    apply to the object itself.

    > (While there are other ways to bypass constness,
    > 'mutable' is by far the cleanest and most self-documenting way of doing it.
    > Basically you are telling at a language level that "this member variable can
    > be modified by const methods.")


    Ok, but I was just aiming to explain the concept, not list ways to
    bypass it.

    /Jorgen

    --
    // Jorgen Grahn <grahn@ Oo o. . .
    \X/ snipabacken.se> O o .
    Jorgen Grahn, Apr 10, 2012
    #14
    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. Engineer
    Replies:
    6
    Views:
    612
    Jeremy Bowers
    May 1, 2005
  2. Replies:
    0
    Views:
    428
  3. MKTMK
    Replies:
    0
    Views:
    306
    MKTMK
    Jul 15, 2005
  4. Lipper, Matthew

    Basic Syntax for Extending Instances

    Lipper, Matthew, Jan 5, 2004, in forum: Ruby
    Replies:
    1
    Views:
    90
    Jamis Buck
    Jan 5, 2004
  5. Ryan Gaffuri

    basic javascript syntax question

    Ryan Gaffuri, Sep 19, 2004, in forum: Javascript
    Replies:
    3
    Views:
    84
    Grant Wagner
    Sep 20, 2004
Loading...

Share This Page