在Java中,对于每个对象,都会创建一个新的实例变量副本,可以使用对象引用进行访问。 但是在实例方法的情况下,只存在它的一个副本(实例方法)。 如何通过各种对象引用访问此方法?
答案 0 :(得分:3)
该方法的字节代码(如果它是JIT的本机代码)存储在一个位置。当调用该方法时,实例对象的指针(在引擎盖下,也就是更高级别的引用)作为第一个参数传递,因此方法代码可以在该特定实例上操作 - 可以访问其字段等。为了节省空间而没有额外的性能成本,Java中的调用机制比C ++复杂得多,尤其是用于接口方法。
答案 1 :(得分:2)
方法和领域完全不同。方法适用于对象的所有实例,但字段是每个实例。
一种思考方式:
假装该方法对所有实例都是“全局的”,但它通过“this”引用“传递”了对象的实例。
方法可以改变特定实例的状态,但它们本身就是无状态的。
答案 2 :(得分:2)
在幕后,对象的引用作为调用的一部分传递给方法。查看Java的反射类,特别是Method.invoke()可能很有用。
答案 3 :(得分:1)
来自之前的answer of mine:
我确信实际的实现是完全不同的,但让我解释一下方法调度的概念,它可以准确地模拟观察到的行为。
假设每个类都有一个哈希表,它将方法签名(名称和参数类型)映射到实际的代码块以实现该方法。当虚拟机尝试在实例上调用方法时,它将获取对象的类,并在类的表中查找请求的签名。如果找到方法体,则调用它,将原始对象提供为名为this
的引用。
否则,获取该类的父类,并在那里重复查找。这一过程一直持续到找到方法,或者没有更多的父类 - 这导致NoSuchMethodError
。
如果超类和子类在其表中都有相同方法签名的条目,则首先遇到子类的版本,并且永远不会使用超类的版本 - 这是“覆盖”。
答案 4 :(得分:1)
隐含的引用“this”被传递给每个方法,当然你可以明确引用
答案 5 :(得分:0)
我假设你的意思很简单,就像你实际上如何进行通话一样。
我还假设您正在引用一种在其签名中具有static
修饰符的方法,即:
public static int getNum()
{
// code in here
return num;
}
如果这是你的意思,这是一个名为“SomeClass
”的类的一部分,那么它将通过方法调用SomeClass.getNum()
访问。即,您将实际的类名放在方法之前。
如果这不是你的意思,请忽略我的回答:)