Thread: passing pointer to a function

  1. #1
    Registered User
    Join Date
    Dec 2004
    Posts
    29

    passing pointer to a function

    Hi@all

    I am studying pointers from my text book. I think I understood the concept but I don't understand between two small programs that I am showing them below. Can you tell me the diffrence between them?

    Thanks

    Code:
    #include <iostream>
    using namespace std;
    
    void function (int *p1);
    
    
    int main()
    {
    	int a=2;
    
    	int *p2=&a;
    
    	cout <<*p2<<endl;
    
    	function (p2);
    
    	cout <<*p2<<endl;
    
    	return 0;
    }
    
    void function (int *p1)
    {
    	*p1=*p1+*p1;
    
    	cout <<*p1<<endl;
    
    
    }
    Code:
    #include <iostream>
    using namespace std;
    
    void function (int *&p1);
    
    
    int main()
    {
    	int a=2;
    
    	int *p2=&a;
    
    	cout <<*p2<<endl;
    
    	function (p2);
    
    	cout <<*p2<<endl;
    
    	return 0;
    }
    
    void function (int *&p1)
    {
    	*p1=*p1+*p1;
    
    	cout <<*p1<<endl;
    
    
    }
    Last edited by Apropos; 02-25-2005 at 09:13 PM.
    Not to know, not to learn is shame

  2. #2
    vae victus! skorman00's Avatar
    Join Date
    Nov 2003
    Posts
    594
    The first one passes only a pointer. The second passes a reference to that pointer (almost like a pointer to a pointer). So in the first example, you can mess with p1 all you want, and p2 will never change. The value it points to may change, but the pointer itself will be the same. In the second example, if you changed p1 within function, for instance by creating a third pointer called p3 and writing p1 = p3; , Then p2 would also change.

    I hope that helps, please ask more questions if it does not.

  3. #3
    Registered User
    Join Date
    Dec 2004
    Posts
    29
    Hi skorman00

    Thanks for the reply but I am still

    Quote Originally Posted by skorman00
    in the first example, you can mess with p1 all you want, and p2 will never change.
    Does it mean that I am passing the pointer to function call by value? If the answer is yes.

    Why when I want to print out the *p2 second time, *P2 is changing?

    Because of calling by value, it shouldn't change right?
    Last edited by Apropos; 02-25-2005 at 09:54 PM.
    Not to know, not to learn is shame

  4. #4
    Registered User
    Join Date
    Jan 2003
    Posts
    311
    You are indeed passing the pointer by value inside your function you have a completely different pointer that has the same value as the pointer you passed into the function. If you then use the pointer to make changes to whatever your pointer points to, then this is the same as if you made changes with the first pointer because they have the same value. consider:
    Code:
    int a = 5;
    int b = a;
    c += b;
    //does the same thing as
    c += a;
    //b has the same value as a, but b is not a;
    int *p1 = &a;
    int *p2 = p1;
    *p2 += 5;
    // does the same thing as
    *p1 += 5;
    //p2 has the same value as p1, but p1 is not p2

  5. #5
    Registered User
    Join Date
    Dec 2004
    Posts
    29
    grib, thanks for your comment.

    I want to pass a pointer call by reference. I wrote a small program that changes the values of the two variables pointed by its arguments. Is this method correct for passing a pointer call by reference?

    Code:
    #include <iostream>
    
    using namespace std;
    
    void swap (int *x,int*y);
    
    int main()
    {
    	int i=10;
    
    	int j=20;
    
    	cout <<"Now first integer is:"<<i<<endl;
    
    	cout <<"Now second integer is:"<<j<<endl;
    
    	swap(&x,&y);
    
    	cout <<"Now first integer is:"<<i<<endl;
    
    	cout <<"Now second integer is:"<<j<<endl;
    	return 0;
    }
    
    void swap (int *x, int *y)
    {
    	int temp=*x;
    
    	*x=*y;
    
    	*y=temp;
    }
    Not to know, not to learn is shame

  6. #6
    Registered User
    Join Date
    Mar 2002
    Posts
    1,595
    The syntax of C++ can be as convoluted as English. This line:

    swap(&x,&y);

    does inded pass x and y to swap() by reference as opposed to by value. Passing by reference can be done by passing a pointer or a reference. In your case you are passing the address of x and y and swap is expecting a pointer to x and y and pointers to x and y are the address of x and y, so everything is fine. However, you should be aware that passing by reference is different than passing a reference and therefore

    " passing a pointer call by reference"

    is somewhat confusing.
    You're only born perfect.

  7. #7
    Registered User
    Join Date
    Dec 2004
    Posts
    29
    hi elad,

    I am little confused now. Whenever I want to use a pointer as an argument in a function call, I have to pass the address that the pointer references to the function right?.

    I know what passing by reference means but I am not sure passing a reference means. Can you give me an example about it?

    thanks for your help
    Last edited by Apropos; 02-26-2005 at 01:46 PM.
    Not to know, not to learn is shame

  8. #8
    Registered User
    Join Date
    Apr 2003
    Posts
    2,663
    I am little confused now. When I want to use a pointer as an argument in a function call, I have to pass the address that the pointer references to the function right?
    You can pass an address or a pointer:
    Code:
    #include <iostream>
    
    using namespace std;
    
    void swap (int *x, int*y);
    
    int main()
    {
    	int i=10;
    
    	int j=20;
    
    	cout <<"Now first integer is:"<<i<<endl;
    
    	cout <<"Now second integer is:"<<j<<endl;
    
    	swap(&x,&y);
    
    	int* pi = &i;
    	int* pj = &j;
    
    	swap(pi, pj);
    
    
    	cout <<"Now first integer is:"<<i<<endl;
    
    	cout <<"Now second integer is:"<<j<<endl;
    	return 0;
    }
    
    void swap (int *x, int *y)
    {
    	int temp=*x;
    
    	*x=*y;
    
    	*y=temp;
    }
    You can pass a 'literal' address(&i, &j) or a variable that stores an address(pi, pj).

    I know what passing by reference means
    There really is no such thing--everything is passed by value. Run this program and carefully examine the addresses that are displayed:
    Code:
    #include <iostream>
    using namespace std;
    
    void func(int* p)
    {
    	int i = 100;
    	p = &i;
    	cout<<p<<endl; //display new address
    }
    
    int main()
    {
    
    	int n = 5;
    	int* pn = &n;
    	cout<<pn<<endl; //display address
    
    	func(pn);
    	cout<<pn<<endl;  //did anything change?
    
    	return 0;
    }
    The first and the second addresses that are displayed should be indentical, which proves a pointer is passed by value--the function cannot permanently change the address stored in the pointer.

    However, you can use a copy of a pointer to permanently change the object stored at that address. It doesn't matter whether you have the original address or a copy of the address--either one can be used to make permanent changes to the object stored at that address.

    ...but I am not sure passing a reference means.
    A reference is implemented as a constant pointer. A constant pointer is a pointer that always has to point at the same address. The value at that address can change, but the pointer cannot be assigned another address.

    Passsing a reference means you are passing a constant pointer to the function, and just like with a regular pointer, a copy is made for the function. References just have a different syntax than pointers. Here is an example:
    Code:
    #include <iostream>
    using namespace std;
    
    void func(int& r)
    {
    	int j = 400;
    	r = j; 
    	cout<<r<<endl;
    
    }
    
    int main()
    {
    
    	int n = 5;
    	int& r = n;
    	cout<<r<<endl; 
    	
    	func(r); 
    	func(n); //Can send a normal variable or a reference variable to the function
    
    	cout<<"after function call: " <<r<<endl;
    
    	return 0;
    }
    Inside the function, this line:
    Code:
    void func(int& r)
    {
    	int j = 400;
    	r = j; 
    	cout<<r<<endl;
    
    }
    is the crucial line. It looks like the reference variable is being made to refer to another variable(i.e. the address is being changed which is not allowed for a constant pointer). However, the syntax of a reference variable hides what is really happening. What is really happening is that a copy of the reference/constant pointer was made for the function, and the assignment statement is using the address of the pointer to change the value at that address--just like when you pass a regular pointer to a function. As an experiment, remove the & in the function parameter, and then run the program again and reexamine the output.
    Last edited by 7stud; 02-26-2005 at 02:49 PM.

  9. #9
    Registered User
    Join Date
    Jan 2003
    Posts
    311
    It's confusing, partially because reference originally refered only to a pointer value, but now we have the language concept of a reference.
    In C the only way to change elements outside of a functions scope is by de-referencing a pointer. The only way these pointers can do that is to give them a reference to what you want to allow the function to change. Thus it's clear that if you want a function to change x, you have to tell that function where x is, address of x aka reference.

    This was common enough that C++ automates the process. swap(int &a, int &b); accepts only references, but in this case, reference is not exactly an address. Inside swap a is an element of your program outside of swap's scope. The compiler can always use a pointer to x to make changes to x, but it also has some powerful options to, in effect, use x directly. On some level this sort of pass-by-reference really doesn't "pass" anything. As to how this all works out in english, I would say that in the call swap(&x, &y);we are passing a pointer to x and y, even though &x is the address of, or a reference to, x and thus x is being "passed by reference"

    [edit]
    7stud:
    The compiler may implement a reference as a contant pointer, but it doesn't have to. You can have a reference to a register for example, but you cannot have a pointer to register.
    Last edited by grib; 02-26-2005 at 02:12 PM.

  10. #10
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    This is passing by reference:
    Code:
    void foo( int &bar )
    {
        bar = 10;
    }
    
    ...
    
    void somefunction( void )
    {
        int x = 0;
    
        foo( x ); // x is passed by reference, since that's what the function takes.
                  // It is (read: can be) modified in the function, just as if you had
                  // passed a pointer to x instead of x itself.
    
        ...
    }
    However, with references, unlike pointers, you can never pass NULL. That is to say, you can have a null pointer, but never a null reference. A reference will always reference something (it has to, or it won't compile--if you can get one to compile, I'd like to see it. ).

    Quzah.
    Hope is the first step on the road to disappointment.

  11. #11
    Registered User
    Join Date
    Jan 2003
    Posts
    311
    Quote Originally Posted by quzah
    A reference will always reference something (it has to, or it won't compile--if you can get one to compile, I'd like to see it. ).
    Code:
    int &r = *(reinterpret_cast<int *>(0));
    This probably won't run teribly long, but it comples just fine

  12. #12
    Registered User
    Join Date
    Apr 2003
    Posts
    2,663
    The compiler may implement a reference as a contant pointer, but it doesn't have to. You can have a reference to a register for example, but you cannot have a pointer to register.
    I am not sure what implication that has, and it seems to me it's a niggling detail that beginners don't need to bother with. The whole concept of passing-by-value and passing-by-reference is overly confusing because I think most C++ books lie about what is happening in an effort to simplify. However, that just makes things confusing later on when things don't work as you would expect.

    Maybe to understand references at a beginning level, you have to be lied to, and as you gain more understanding of C++, the lies can be revealed to you one by one. There was always a lingering uncertainty in the back of my mind about references and pointers until Salem or Prelude posted that references are just constant pointers with a syntax that hides what is really happening. That cleared everything up for me, but maybe further on down the road, I will once again encounter other uncertainties.
    Last edited by 7stud; 02-26-2005 at 02:40 PM.

  13. #13
    Registered User
    Join Date
    Jan 2003
    Posts
    311
    Quote Originally Posted by 7stud
    I am not sure what implication that has, and it seems to me it's a niggling detail that beginners don't need to bother with. The whole concept of passing-by-value and passing-by-reference is overly confusing because I think most C++ books lie about what is happening in an effort to simplify. However, that just makes things confusing later on when things don't work as you would expect.

    Maybe to understand references at a beginning level, you have to be lied to, and as you gain more understanding of C++, the lies can be revealed to you one by one. There was always a lingering uncertainty in the back of my mind about references and pointers until Salem or Prelude posted that references are just constant pointers with a syntax that hides what is really happening. That cleared everything up for me, but maybe further on down the road, I will once again encounter other uncertainties.
    It's somewhat of a deep philosphical issue, const pointers that can only be initalised and are always dereferenced is something very close to a reference. Same deal with "an array is a const pointer" . The problem is that by lieing to the user, they end up in essence lieing to thier compilers. If you want a const pointer, you should ask for one. It might be pendantry, but I think that it's better to think of referneces as a way for others to work with things in my scope, and as a way to work with things in other scopes. Pointers are a way to change what you are working with. It can be understood at the level of the machine language, but I think that the higher level offers a better understanding. Part of the charm of C is that it's really just a portable or vague assembler, but I think it's better to try to keep to the vague or high level side. This get's the compiler to do as much work as possible. For me, references just seemed annoying at first, because I learned C and assembler before C++. In c you can always tell when you are going to change something because you have to "load it's address" into a register. It wasn't until I realised that swap and the function calling swap could use the same register for x, and swap simply uses a different name for that same register that I began to see the point. It wasn't until I stopped asking for the assembly language program in my mind that I began to actually be able to write C++, rather than being disapointed in the lousy assembler that can't see that I don't need to preserve EAX.

    When I see people calling references pointers I think that they are probably still talking to that assembly language program in thier minds. A lot of good programmers do this, Linus is famous for looking at the assembly output and changing things to get exactly what he wants. I'm probably just confusing everyone but these are the things that helped me to understand how to program well, or at least better, if you can work within the terms of the language itself, you begin to ask for results, rather than things. Yep, I'm defenatly just confusing everyone.

  14. #14
    Registered User
    Join Date
    Dec 2004
    Posts
    29
    @grib and 7stud;

    Thanks for the lectures. I just got in pointers so I found 7stud examples very helpful. it is not easy to understand but you guys helped me to understand pointers and references. I am appreciated.

    @grib

    I think you are talking at professional level. One day I will understand your last two commends but it is hard for me to understand now.

    After understanding the concept of pointers, it is time to study. Two programs are waiting to be written
    Not to know, not to learn is shame

  15. #15
    Registered User
    Join Date
    Apr 2003
    Posts
    2,663
    I'm glad I didn't confuse you more.

    It doesn't really matter what you call it, but if the function parameter is a pointer or a reference, you can permanently change the object. I hope you tried removing the & from the function parameter in that example. It shows that it doesn't matter whether you send an object or the reference/alias for the object, if the function parameter has that little &, then you can permanently change the object, otherwise you can't.
    Code:
    #include <iostream>
    using namespace std;
    
    void func(int& r)
    {
    	int j = 400;
    	r = j; 
    	cout<<"in function: "<<r<<endl;
    
    }
    
    int main()
    {
    	int x = 10; //notice x is not a reference variable
    	cout<<"original: "<<x<<endl;
    
    	func(x);
    	cout<<"back in main(): "<<x<<endl;
    
    	return 0;
    }
    Note that it doesn't matter whether x is a reference variable or not--it only matters what the function parameter says, and that determines how x will be treated inside the function--will it be allowed to change the original(int& r) or only change the copy(int r)?
    Last edited by 7stud; 02-26-2005 at 05:49 PM.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. sorting number
    By Leslie in forum C Programming
    Replies: 8
    Last Post: 05-20-2009, 04:23 AM
  2. Replies: 9
    Last Post: 12-25-2007, 05:01 AM
  3. Game Pointer Trouble?
    By Drahcir in forum C Programming
    Replies: 8
    Last Post: 02-04-2006, 02:53 AM
  4. pointers
    By InvariantLoop in forum C Programming
    Replies: 13
    Last Post: 02-04-2005, 09:32 AM
  5. Passing a function pointer to a templated type
    By skorman00 in forum C++ Programming
    Replies: 2
    Last Post: 04-13-2004, 08:31 PM