所以我开始学习C++,并发现了这个例子——
#include <iostream>
void doIt(int x)
{
x = 3;
int y = 4;
std::cout << "doIt: x = " << x << " y = " << y << std::endl;
}
int main()
{
int x = 1;
int y = 2;
std::cout << "main: x = " << x << " y = " << y << std::endl;
doIt(x);
std::cout << "main: x = " << x << " y = " << y << std::endl;
return 0;
}
--对于调用 doIt(( 的序列,打印 doit: x = 3 y = 4。也许我可以搜索一些未知的东西来更好地了解发生了什么,但本质上我想知道的是 x 是作为变量还是作为其值 (1( 传递给函数。如果它作为 1 传递,会不会有错误?这是否意味着该函数需要整数变量而不是独立整数?该程序旨在显示这些变量如何是局部的,但我不确定它们是如何组合在一起的。
当你将一个整数传递给函数doIt(int x)
时,你传递的int
将被复制。 因此,您对doIt()
体内x
所做的任何事情都将是存在于doIt()
的副本所独有的
请注意,变量的名称可以相同,也可以不同。 这没有什么区别。 如果您通过 VALUE 传递,则始终复制变量内容。
#include <iostream>
void doIt(int x) //x here is completely different value than in main
//even though they have the same name
{
x = 3; //this variable has its own scope
int y = 4;
std::cout << "doIt: x = " << x << " y = " << y << std::endl;
} //at the end of this function x is destroyed
int main()
{
int x = 1;
int y = 2;
std::cout << "main: x = " << x << " y = " << y << std::endl;
doIt(x); //the content of variable x will be passed by value to doIt()
std::cout << "main: x = " << x << " y = " << y << std::endl;
return 0;
}
还有另一种方法可以在C++中传递参数,即通过引用语义传递。 它看起来像这样:
void doIt(int &z) //z is passed by reference, changing it will stick
//z is the SAME variable that was passed in, even if the name is different
{
z = 3; //this will change the value that was passed in
int y = 4;
std::cout << "doIt: z = " << x << " y = " << y << std::endl;
} //z is not destroyed here, because it wasnt created in this scope
int main()
{
int x = 1;
int y = 2;
std::cout << "main: x = " << x << " y = " << y << std::endl; //x is 1
doIt(x);
std::cout << "main: x = " << x << " y = " << y << std::endl; //x is 3 now
return 0;
}
通过引用传递将通过其内存地址"秘密"发送变量,因此函数接收的int
实际上与传入的相同。请注意,我选择了变量名称 z,因为不同作用域中的变量名称实际上并不重要。
变量不会传递给函数 - 值是。(如果我们说"变量被传递给函数",它只是说变量的值被传递给函数的缩写(
当调用doIt
时,doIt
中的x
和y
是全新的变量,与main
中的变量无关。第一个参数的值(即 main
中 x
的值,即 1(存储在 x
中。然后,3 存储在 x
中(由行 x = 3;
(。然后,4存储在y
中。然后打印 x
和 y
,其中包含值 3 和 4。
一旦doIt
返回,main
的变量就不会被更改,因为它们是不同的变量(巧合的是具有相同的名称(。所以main
再次打印 1 和 2。
按值传递,但在方法中创建一个新的 x。新的 x 会将值传递到方法中。新的 x 在作用域上仅限于方法:局部变量。
您可以像代码一样为本地 x 分配一个新值。它不会影响调用方法中的变量。
当函数采用纯参数(例如int x
(时,编译器会将VALUE传递给被调用的函数(也称为"被调用方"(。在被调用方内部,该值存储在局部变量 [1] 中,因此当您通过说 x = 3
来更新它时,函数内的 COPY 会更新,而不是调用方中的原始值。
这是一件好事,因为这意味着您可以将值传递给函数,而不必知道函数是否更改它。
如果要修改输入变量的值,它需要是一个引用,void doIt(int &x)
- 在这种情况下,编译器将通过引用传递实际变量,以便您可以修改它[从技术上讲,这意味着传递变量的地址,而不是它的内容,然后在被调用方中传递相关代码来处理差异]。
[1] 是的,从技术上讲,该复制通常是在调用方代码处完成的。