指针:指针是一个变量,用于保存另一个变量的内存地址。需要使用*运算符取消引用指针,以访问其指向的内存位置。
引用:引用可以称为常量指针,它被隐式取消引用。当我们访问引用时,这意味着我们正在访问存储。
如果有指针,为什么需要引用变量?
在指针中访问实际变量的值时,我们需要通过使用“地址处的值”解引用运算符(*)显式地引用指针变量。
在引用中访问实际变量的值时,我们不需要显式地取消引用该引用变量,它们会自动被取消引用。
指针和引用是等效的,除了:
- 引用就像地址的常量名称。我们需要在声明期间初始化引用。 一旦建立了对变量的引用,我们就不能将引用更改为引用另一个变量。
- 要获得指针指向的值,我们需要使用解引用运算符(*) 。
For Example: If a is a pointer to integer type, *a returns the value pointed to by a.
To assign an address of a variable b into a pointer, we need to use the address-of operator(&).
For Example: int *a= &b. - 引用用于指针以避免对象切片。
Object slicing happens when a derived class object is assigned to a base class object, additional attributes of a derived class object are sliced off to form the base class object.
- 在引用中,引用和取消引用是隐式完成的。没有显式的取消引用运算符(*),并且没有将变量的地址分配给引用变量,也没有地址运算符(&)。
- 参考变量为现有变量提供了新名称。它隐式地取消引用,不需要引用运算符(*)即可检索引用的值。而要检索指针所指向的值,我们需要解引用运算符(*) ,这称为显式解引用。
- 引用可以视为常量指针。它必须在声明期间初始化,并且其内容不能更改。
以下是用于说明指针和参考的程序:
C++14
// C++ program to illustrate
// pointer and references
#include
using namespace std;
// function to illustrate
// pointer and references
void pointer_vs_reference()
{
int num1 = 20, num2 = 23;
// Pointer pointing to num1
// Explicit referencing
int* ptr1 = &num1;
cout << *ptr1 << endl; // 20
// Explicit dereferencing
*ptr1 = 26;
cout << *ptr1 << endl; // 26
// pointer can be reassigned to
// store another address
ptr1 = &num2;
cout << *ptr1 << endl; // 23
// Reference to num1
// Implicit referencing
int& ref1 = num1;
cout << ref1 << endl; // 26 not 20
// Implicit dereferencing
ref1 = 18;
cout << ref1 << endl; // 18
// reference cannot be reassigned
}
// Driver code
int main()
{
pointer_vs_reference();
return 0;
}
C++
#include
using namespace std;
class complex {
private:
int a, b;
public:
// Parametric constructor
complex(int x, int y)
{
a = x;
b = y;
}
// Copy constructor
complex(const complex& c)
{
a = c.a;
b = c.b;
}
// Function to print data
void printData()
{
cout << "a = " << a << endl;
cout << "b = " << b;
}
};
int main()
{
complex c1(5, 10);
complex c2(c1);
c2.printData();
}
20
26
23
26
18
输出说明:
- 当指针ptr指向num1 var时,它打印了20
- 当取消引用* ptr并更改值时,它打印了26
- 与另一个名为num2的变量相似,已打印23
- 当引用ref1由num1初始化时,它打印了26个而不是20个
- 最后,当将18分配给ref1时,由于隐式取消引用,它打印了18
参考变量的图示:
引用变量的最佳示例是复制构造函数的概念。复制构造函数将引用变量作为参数,此处不能使用指针。
C++
#include
using namespace std;
class complex {
private:
int a, b;
public:
// Parametric constructor
complex(int x, int y)
{
a = x;
b = y;
}
// Copy constructor
complex(const complex& c)
{
a = c.a;
b = c.b;
}
// Function to print data
void printData()
{
cout << "a = " << a << endl;
cout << "b = " << b;
}
};
int main()
{
complex c1(5, 10);
complex c2(c1);
c2.printData();
}
a = 5
b = 10
说明:在上面的示例中,如果我们在复制构造函数的参数中使用指针,那么将一次又一次地创建复杂类的对象,该对象将永远不会停止,这是oops概念中的错误。选择参考只是在这种情况下的解决方案。