-2

I am getting segmentation fault in first code but the second code is running fine, don't know how?

How can I copy a pointer and save it to another pointer?

#include <iostream>

using namespace std;

int main() {
    int *p;
    int *p1;
    *p1=7;
    p=p1;
    cout<<*p<<" "<<p;
    return 0;
}
#include <iostream>

using namespace std;

int main() {
    int *p1;
    *p1=7;
    int *p=p1;
    cout<<*p<<" "<<p;
    return 0;
}    
//7 0x7ffeea73db70
anastaciu
  • 23,467
  • 7
  • 28
  • 53
  • 1
    As the old saying goes, "undefined behaviour is undefined". That one of them runs is just bad luck. – molbdnilo Mar 17 '20 at 14:04
  • 1
    How you allocate memory for your pointers `p` and `p1`?! – Landstalker Mar 17 '20 at 14:05
  • Related: [(Why) is using an uninitialized variable undefined behavior?](https://stackoverflow.com/questions/11962457/why-is-using-an-uninitialized-variable-undefined-behavior?noredirect=1&lq=1) It's not strictly about pointers, but UB is just the same. – Yksisarvinen Mar 17 '20 at 14:06
  • 1
    It would be Undefined Behavior even if you didn't try to assign `7` to `*p1`. You can't even copy an uninitialized pointer, let alone dereference it. – MSalters Mar 17 '20 at 14:07
  • 2
    @Yksisarvinen: That's C, not C++. The rationale is similar, but the formal rules are different. – MSalters Mar 17 '20 at 14:08
  • I recommend you enable your compiler warnings. That will help guide you from making these kinds of mistakes. – Eljay Mar 17 '20 at 15:00

2 Answers2

4

Both cases invoke undefined behaviour, in both cases you make use of uninitialized pointer p1, the fact that the second case "works" for you is a matter of sheer luck, as you can see here.

For your code to be valid you need to make it point to a valid memory address either by allocating memory manually:

int *p1 = new int; //raw pointer, (better to use smart pointers* but let's not get ahead of ourselves).

Or by assigning it the address of a valid int variable:

int i = 5;
int *p1 = &i;

How can I copy a pointer and save it to another pointer?

A pointer is essentially a variable like any other, you can copy it like you do a normal primitive variable, in fact you do just that when you do p = p1, these are two different pointers that will now contain the same value, the address of the variable they point to.

This code exemplifies this

#include <iostream>

using std::cout;
using std::endl;

int main() {

    int *p1 = new int;
    *p1 = 7;
    int *p = p1;
    cout<< "Value stored in the address p points to: " << *p << endl  
        << "Value stored in the address p1 points to: " << *p1 << endl
        << "Address where p points to: " << p 
        << " " << endl <<  "Address where p1 points to: "<< p1 
        << endl << "Address of p: " << &p << endl << "Address of p1: "<< &p1;

    return 0;
} 

The output:

Value stored in the address p points to: 7
Value stored in the address p1 points to: 7
Address where p points to: 0x804150 
Address where p1 points to: 0x804150
Address of p: 0x7ffc9447e220
Address of p1: 0x7ffc9447e228

*What is a smart pointer and when should I use one?

anastaciu
  • 23,467
  • 7
  • 28
  • 53
2

When you dereference an int* pointer, you promise that there is an int object at that address. C++ believes you, often without questioning. But you never wrote int a; p1=&a; or any other code that made sure p1 points to an actual int.

In fact, p1 isn't even a null pointer. The only thing you can do with p1 is to assign it a legal value. That is to say, it must appear at the left-hand side of an assignment first. It can't be used on the right hand side in int* p = p1;

MSalters
  • 173,980
  • 10
  • 155
  • 350