我在Java字節碼規範中發現了一些我不明白的東西。Java字節碼中的字段引用
考慮下面的類層次結構:
class FilterOutputStream {
protected OutputStream out;
}
class PrintStream extends FilterOutputStream {
public void write(...) {
out.write(...);
}
}
縱觀字節碼的PrintStream與javap的,我看到在讀了out
場像這樣做:
getfield #21
參考#21,如預期的那樣,Field引用包含該字段的類,名稱和描述符。然而,它看起來像這樣:
const #21 = Field #30.#204; // java/io/PrintStream.out:Ljava/io/OutputStream;
這實在令人費解,因爲這表示,out
場是PrintStream的一員。這不是真的;它是FilterOutputStream的成員,這是我期望在上面的字段引用中看到的類。 JVM規範相當模糊,但似乎支持我:
class_index項的值必須是常量池表中的有效索引。 該索引處的constant_pool條目必須是CONSTANT_Class_info(§4.4.1)結構 ,表示將該字段或方法作爲成員的類或接口類型。
(從http://docs.oracle.com/javase/specs/jvms/se7/html/jvms-4.html#jvms-4.4.2)
這對我來說是一個問題,因爲我實地考察一下參考,加載類,然後無法找到的領域。另一方面,Java編譯器可以工作,所以顯然我的理解是錯誤的...
有人可以爲我澄清一下嗎?我是否應該加載這個類,尋找字段引用,如果沒有找到,那麼直到找到它時纔開始處理類層次結構?
指針到規範的地方它描述了這樣做的正確的行爲,將不勝感激......
謝謝!正是我在找什麼。 (自從上一次我做了關於字節碼的詳細工作後,這實際上已經發生了_changed_變化。接口上的字段?這是錯誤的......) –