作者macbuntu (邀怪)
看板PLT
標題[問題] compiler 該如何處理這種 circular dependency
時間Tue Jul 14 12:11:00 2009
以 java 的語法為例 (這種 dependency 是合法的):
class A {
void funcA(B b) {
b.funcB(this); // A depends on B
}
}
class B {
void funcB(A a) {
a.funcA(this); // B depends on A
}
}
Compiler 在處理 A 的時候, 必須知道 B 的定義才能處理 b.funcB(),
但是要定義 B, 又必須知道 A 的定義才能處理 a.funcA()...
我現在寫的 compilier 是先掃第一次只定義所有型別的介面, 再掃第二次
處理 method 內的 statements; 但是在處理 statements 的時候可能會遇到
新的型別, 就又要回去定義, 整個架構變得有點亂...
想問問有沒有人知道一般 compiler 是用什麼架構處理這種問題的?
--
※ 發信站: 批踢踢實業坊(ptt.cc)
◆ From: 60.251.144.115
1F:推 noctem:我知道有些 compiler 會在第一個 pass 先把 interface 的 07/14 15:07
2F:→ noctem:相關資訊寫到一個檔案裡面,然後再做第二個 pass. 07/14 15:07
3F:→ noctem:基本上都是要兩個 pass 囉..? 07/14 15:08
4F:→ Schelfaniel:為什咩掃第二次時會出現新的型別?? 07/14 18:33
5F:推 godfat:因為實作裡可能用到介面沒出現的型別? 07/14 20:17
6F:→ godfat:所以掃型別時,可能要連實作都要掃,不能只看介面? 07/14 20:18
7F:→ macbuntu:對, 譬如實作裡出現 Foo o; 宣告, 這個 Foo 就是新的 07/14 21:58
8F:→ macbuntu:在所有型別介面沒確定前, 直接掃實做也不行, 譬如 07/14 22:01
9F:→ macbuntu:X.Y.Z(); 就無法知道 Y 是 package 還是 field name, 07/14 22:02
10F:→ macbuntu:得定義完 X 才能確定, 所以也沒辦法第一次就連實做掃 :( 07/14 22:04
11F:→ Schelfaniel:可是型別不是會要事先宣告?? 07/15 11:04
12F:→ Schelfaniel:Java 有 package 名稱建議小寫,大概就是怕混淆。 07/15 11:10
13F:推 godfat:宣告也是在實作裡宣告,沒寫在介面上,至於 package... 07/15 11:42
14F:→ godfat:我想這大概是為什麼 ActionScript 強迫你用 import 吧 :s 07/15 11:43