2009-11-11 104 views
7

有些功能是很容易在OCaml中實現(例如,從列表地圖),但你可以使用OCaml的庫圖:List.mapOCaml的模塊和性能

但是,我們可以知道哪些代碼會更有效率。調用單獨編譯單元(庫)的模塊可能會使一些可能的優化失效。我在新聞組fa.caml中讀到,當從庫中調用函數時,會使用閉包。

我在生產中使用模塊和函數進行泛型編程的OCaml代碼。由於歷史原因,我的代碼是monolitic:全部在一個文件中。現在我有更多的時間,我願意將代碼分離成這些模塊的文件。但是,恐怕我會失去表現,因爲我花了一段時間才弄清楚了。例如,我有用於用數字包裝複雜對象的模塊,因此我執行了獨特的表示和快速比較。我將這些包裝的對象與通用的地圖,集合一起使用,並在其上構建緩存。

的問題是:

  • 我要去鬆動的表現,如果我移動到單獨的文件?
  • OCaml是否對我的模塊,仿函數等代碼做了很多優化?

在C++中,如果您在.h中定義類方法,編譯器可能會結束內聯短方法等。是否可以使用分隔文件在OCaml中實現該方法?

+0

我不太瞭解ocaml編譯器和鏈接器的內部,所以我無法回答你的問題。但是,如果您將代碼分解爲模塊而失去了性能,那麼我會非常驚訝。即使你確實損失了幾毫秒,代碼的清晰度也會提高。 – 2009-11-11 19:29:51

+0

在C/C++中可能會導致巨大的差異。我擁有數百萬個對象,訪問/比較了數十萬次。每次訪問的一組輔助參考可能非常糟糕。 – hectorpal 2009-11-12 06:56:32

+0

是的,但是編譯器應該內聯這些引用,以便實際上不需要進行更多的查找。你如何試着用一堆虛擬模塊做一個測試項目,並試着衡量把它們分解並保存在同一個文件中是否有區別。這可能比重構工作代碼庫少很多。希望這會給你更多的信心,ocamlopt將能夠智能地優化你的代碼。 – 2009-11-13 19:42:20

回答

9

您可能會失去一些性能。但是,有兩個緩解因素:

  • OCaml的本地代碼編譯器可以做跨模塊內聯,所以它是可能的代碼,甚至跨越不同的編譯單元內聯(與一對夫婦告誡 - 遞歸函數和函數參數不跨模塊[1])內聯。
  • 代碼仍然很可能足夠快,可讀性和可維護性的提高很可能會超過任何(邊際)性能成本。

我不知道OCaml defunctorizes函數在同一個源文件中定義的代碼。如果沒有,那麼模塊不應該增加任何已經由仿函數引起的性能。

一般來說,我認爲最好是編寫簡單易讀,可維護的代碼,而不必太擔心這樣的微觀性能特性,除非代碼在實踐中證明速度太慢。

+0

謝謝邁克爾。好信息。當然,我知道我會獲得可讀性。我現在所擁有的並不令人滿意。但是,在我的情況下,運行時性能是一個關鍵問題。我已經投入了很多時間從列表切換到數組(我正在使用Res庫來增加數組)。我也有大量的緩存並仔細選擇數據結構。我認爲我做了我所做的事情,從10分鐘或10分鐘降至10秒。我現在關心的主要是關於用數百萬個對象來表示的模塊。無論如何,我會分裂,但我需要表明這種影響,並且不得分裂所有。 – hectorpal 2009-11-12 06:52:04

+0

一旦完成重構代碼,根據需要選擇性地將某些模塊移回主文件應該相對容易。 – 2009-11-18 09:18:22