Wrox Programmer Forums

Need to download code?

View our list of code downloads.

Go Back   Wrox Programmer Forums > C# and C > C++ and Visual C++ > BOOK: Ivor Horton's Beginning Visual C++ 2005
Password Reminder
Register
Register | FAQ | Members List | Calendar | Search | Today's Posts | Mark Forums Read
BOOK: Ivor Horton's Beginning Visual C++ 2005
This is the forum to discuss the Wrox book Ivor Horton's Beginning Visual C++ 2005 by Ivor Horton; ISBN: 9780764571978
Welcome to the p2p.wrox.com Forums.

You are currently viewing the BOOK: Ivor Horton's Beginning Visual C++ 2005 section of the Wrox Programmer to Programmer discussions. This is a community of tens of thousands of software programmers and website developers including Wrox book authors and readers. As a guest, you can read any forum posting. By joining today you can post your own programming questions, respond to other developersí questions, and eliminate the ads that are displayed to guests. Registration is fast, simple and absolutely free .
DRM-free e-books 300x50
Reply
 
Thread Tools Display Modes
  #1 (permalink)  
Old March 5th, 2007, 04:55 PM
Authorized User
 
Join Date: Dec 2006
Location: , , .
Posts: 34
Thanks: 0
Thanked 0 Times in 0 Posts
Default declaring constants and pointer constants

Ok, my last post about const member functions was a simple mistake (if
you read it, sorry).

But, I'm having trouble making sense of the syntax for for declaring
constant pointers. When I google 'c++ const pointers' I get articles
with seemingly conflicting info.

Anyone have a formula on how I should "say it in my head" when writing
sytax like: "const int const* pb = &b;" or "const int* pb = &b"???

Here's my dilemma: In the code below, I thought "const int const* pb = &b;" would be constant pointer to a constant integer, but I can change the pointer to the address of variable 'a' with no problem. (gcc compiler will complain about duplicate 'const' though

Thanks in advance!

thanks,
Brian
-----
Code:
#include <iostream>

using namespace std;

int main(void)
{
  int a = 5;
  const int b = 10;

  int* pa = &a;
  const int const* pb = &b;
  const int* pvb = &b;

  cout << "const int const* pb = &b; " << (long)pb <<;
  cout << endl << "const int* pvb = &b; " << (long)pvb << endl <<
endl;

  pb = &a;
  pvb = &a;

  cout << "pb = &a; " << (long)pb << endl;  
  cout << "pvb = &a; " << (long)pvb << endl;  

  return 0;
}

Sincerely,
Brian
__________________
Sincerely,
Brian
Reply With Quote
  #2 (permalink)  
Old March 6th, 2007, 11:47 AM
Authorized User
 
Join Date: Feb 2007
Location: , , United Kingdom.
Posts: 11
Thanks: 0
Thanked 0 Times in 0 Posts
Default

Hi Brian,

I've had a bit of a scout around on this. I've not had the need to do this before so I've never really investigated it. So I'm no expert. But based on what I've just read and what seems to work in Visual Studio and gcc, this is how I think it works.

If you want to declare a constant pointer to a normal variable, this is how it's done:

    int a = 5;
    int *const pa = &a;

    *pa = 10; // The value of a can be altered through the pointer pa.


You will be able to alter the value of 'a', but you won't be able to alter the value of 'pa' - you'll get a compiler error.

If you want to declare a normal pointer to a constant variable, this is how it's done:

    const int a = 5;
    const int* pa = &a;

In this case, you'll be able to alter value of 'pa' but you won't be able to change the value of 'a' through the pointer. You'll again get a compiler error

if you try to do that.

You can achieve a similar effect by leaving out the const in the declaration of 'a'.

    int a = 5;
    const int* pa = &a;

There is a subtle difference here though. You won't be able to change the value of 'a' through the pointer, but you will be able to change it using a normal assignment statement.

If you want to declare a constant pointer to a constant variable, this is how it's done:

    const int a = 5;
    const int *const pa = &a;

In this case you won't be able to alter either the value of 'a' or the address pointed to by 'pa'.

I think that covers most of the scenarios you might want. I've been trying to think of a succint way you can reason it out when you're writing code. What follows is my best effort.

*** If you want to make a pointer constant, you can add '*const' after the type specifier (the int or char or float or whatever) in the pointer declaration.

*** If the variable that you are pointing to is a constant, or you wish to make it a constant as far as the pointer is concerned, you can place the keyword 'const' before the type specifier in the pointer declaration.

I hope that helps. Sometimes for issues like this where C++ is very similar to C, it's worth looking at some C documentation. It can sometimes point in the right direction. If you want more info take a look at:

http://msdn.microsoft.com/library/de...clarations.asp

All the best with your programming.

Dan

Reply With Quote
  #3 (permalink)  
Old March 6th, 2007, 12:37 PM
Authorized User
 
Join Date: Feb 2007
Location: , , United Kingdom.
Posts: 11
Thanks: 0
Thanked 0 Times in 0 Posts
Default

Hi Brian,

Just another bit of information which might help clarify things.

It seems to be that in the declaration of a pointer, the position of the type-qualifier (the const term in this case) relative to the '*' determines what the type-qualifier applies to. If the const term appears before the '*' in the pointer declaration, it applies to the object pointed to by the pointer. Hence both of these terms are two ways of declaring a pointer which may be altered, while the object pointed to is a constant.

    const int *pa;
    int const* pa;

This explains why you get the complaint about multiple 'const' declarations when you write 'const int const* pb = &b' and why your pointer is not actually a constant itself.

If the 'const' term appears after the '*' in the pointer declaration however, it applies to the pointer itself and not to the object it points to. Hence to declare a constant pointer you have to write:

    int *const pa = &a;

I haven't actually tried this out, so please give it a go yourself before taking my word for it. But it's what seems to be indicated in Kernighan and Ritchie (a C reference book), and makes sense with what's on the web page I refrenced in the previous post.

Anyway, just thought that little piece of information might be worth sharing.

Dan

Reply With Quote
  #4 (permalink)  
Old March 6th, 2007, 02:32 PM
Authorized User
 
Join Date: Dec 2006
Location: , , .
Posts: 34
Thanks: 0
Thanked 0 Times in 0 Posts
Default

Thanks Dan for the wealthy reply. I'm reviewing your material now, but I wanted to share a reply I received from a newsgroup on this. The main idea from the newsgroup was to read the declaration backwards. There are a few details in doing this, and a link was given to check the details. (see below)

The main thing that was messing me up, (after syntax) was the idea of "array of pointers" and "pointer to array". The reason this wasn't making sense in my head is because any time I ever assigned an address of a char array to an array of pointers, I saw only one pointer in a memory dump - pointing to the first item in the char array. This makes sense, but it wasn't clicking with me that I only assigned an address to one pointer, so there should be only one pointer showing.

So, I came up with a little code segment that helped me see it properly in memory dumps (disassembly debug). I declared a normal array *globally* and another normal array locally, in the main function. I knew this would cause the normal arrays to be placed in different areas in memory, then I created an array of pointers (after reviewing the link I discussed in the 1st paragraph here, and provided below). I fill the array of pointers manually with the addresses of the normal global array elements and the normal local array elements. This makes it easy to see that an array of pointers are consecutive pointers in memory, but each consecutive pointer can point to any where else...

here's the code I produced, and the usenet response is pasted in below (alt.comp.lang.learn.c++ with same subject as this post)
Code:
#include <iostream>

using namespace std;

int oranges[2] = {3,4};

int main(void)
{
  int apples[2]= {1,2};

  int * foo[4];
  foo[0] = &apples[0];
  foo[1] = &apples[1];
  foo[2] = &oranges[0];
  foo[3] = &oranges[1];

  return 0;
}
Quote:
quote:
> Anyone have a formula on how I should "say it in my head" when writing
> sytax like: "const int const* pb = &b;" or "const int* pb = &b"???

Yes, the conventional approach is to start at the identifier (in this
case, "pb") and read right to left. So in your case, you would read the
first item as:

declare pb a pointer to constant int constant

As you can see, constant int constant is redundant so one of those
consts is unnecessary.

The second item is:

declare pb a pointer to int constant

This means the same thing as the first declaration, minus the redundant
const. (Note that const int and int const are semantically equivalent
so you could as declare this as: int const* pb = &b).

What you might have mean in the first declaration is: const int * const
pb = &b which means:

declare pb a constant point to int const

The difference of course is that now the pointer itself is constant
(i.e., it can't point somewhere else) in addition to pointing to a
constant int.

If you happen to be on a unix based system you might try playing around
with the command: c++decl

Also check out the following link which goes into considerable more
detail on this subject, including the more complex terrain of function
pointers:

http://www.ericgiguere.com/articles/...larations.html

Sincerely,
Brian
Reply With Quote
Reply


Thread Tools
Display Modes

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 Off
HTML code is Off
Trackbacks are Off
Pingbacks are On
Refbacks are Off

Similar Threads
Thread Thread Starter Forum Replies Last Post
A newer's declaring Ant_Yan J2EE 0 September 15th, 2007 12:35 AM
Constants in XSL austinf XSLT 2 August 29th, 2006 06:04 AM
Declaring a dropdownlist Rod Merritt BOOK: ASP.NET Website Programming Problem-Design-Solution 0 August 1st, 2006 02:11 PM
Global/Public Constants elansolutionsltd Access 6 May 13th, 2005 12:22 PM
DriveType constants fordrs3 Beginning VB 6 1 June 22nd, 2003 08:23 AM



All times are GMT -4. The time now is 10:08 PM.


Powered by vBulletin® Version 3.7.0
Copyright ©2000 - 2014, Jelsoft Enterprises Ltd.
© 2013 John Wiley & Sons, Inc.