【发布时间】:2011-12-28 03:58:11
【问题描述】:
谁有权决定?
编辑:显然我没有成功地提出我的问题。
我不是询问Java 的参数传递是如何工作的。我知道看起来像持有对象的变量实际上是持有对对象的引用的变量,并且该引用是按值传递的。
这里(在链接的线程和其他线程中)和其他地方对该机制有很多很好的解释。
问题是关于术语的技术含义传递引用。 (结束编辑)
我不确定这是否是 SO 的正确问题,如果不是,请道歉,但我不知道更好的地方。在这里的其他问题中已经说了很多,例如Is Java "pass-by-reference" or "pass-by-value"?和pass by reference or pass by value?,但我还没有找到关于这个词的含义的权威答案。
我曾经认为“按引用传递”是指“将引用(通常是指针)传递给对象”,因此被调用者可以修改调用者看到的对象,而“按值传递”意味着复制对象,并且让被调用者享受副本的乐趣(很明显的问题:如果对象包含引用、深拷贝或浅拷贝怎么办)。
唱 FW 出现 lots of places saying “按引用传递”的意思就是,here 有人认为它意味着更多,但定义仍然是
一种ParameterPassing模式,其中对实际参数的引用(或者如果您想政治不正确,则为指针)传递给形式参数;当被调用者需要形式参数时,它会取消引用指针来获取它。
我没有找到很多地方对这个术语给出更严格的定义,在this页面上,我发现“形参的左值设置为实参的左值”。而且,如果我理解正确的话,使用相同的定义here(“形式参数仅充当实际参数的别名。”)
事实上,我发现使用更强定义的唯一地方是反对在 Java 中通过引用传递对象的概念(这可能是由于我缺乏 google-fu)。
所以,如果我把事情弄明白了,就通过引用传递
class Thing { ... }
void byReference(Thing object){ ... }
Thing something;
byReference(something);
根据第一个定义大致对应于(在C中)
struct RawThing { ... };
typedef RawThing *Thing;
void byReference(Thing object){
// do something
}
// ...
struct RawThing whatever = blah();
Thing something = &whatever;
byReference(something); // pass whatever by reference
// we can change the value of what something (the reference to whatever) points to, but not
// where something points to
从这个意义上说,Java 通过引用传递对象就足够了。但是根据第二个定义,传递引用意味着或多或少
struct RawThing { ... };
typedef RawThing *RawThingPtr;
typedef RawThingPtr *Thing;
void byReference(Thing object){
// do something
}
// ...
RawThing whatever = blah();
RawThingPtr thing_pointer = &whatever;
byReference(&thing_pointer); // pass whatever by reference
// now we can not only change the pointed-to (referred) value,
// but also where thing_pointer points to
而且由于 Java 只允许你拥有指向对象的指针(限制你可以用它们做什么)但没有指向指针的指针,从这个意义上说,说 Java 通过引用传递对象是完全错误的。
所以,
- 我是否充分理解了上述传递引用的定义?
- 还有其他定义吗?
- 是否已达成共识,哪个定义是“正确的”,如果是,是哪个?
【问题讨论】:
-
我主要不使用 Java,但我认为它不能通过引用传递任何东西,例如 VB.NET 的
ByRef或 C# 的ref。我想人们所说的“通过引用传递”的实际意思是“通过值传递引用类型”。 -
我认为您误解了第二个示例 - 实际上您通过引用传递的不是
whatever,而是thing_pointer。 -
据我所知:Java 使用按值传递。这意味着对于原始类型,值被复制到形式参数中。对于对象引用,这意味着:引用被复制到形式参数中,因此您将获得按引用传递的行为
-
也许最简洁的表述方式是“所有(类类型)变量都是引用,所有引用都按值传递”。你知道 C++ 吗?这将允许一个明确的答案。
标签: java parameters terminology pass-by-reference