2016-08-18 75 views
1

我特別試圖測試Cjoures聲稱它可以「無縫地」與Java一起工作。一般來說,如何翻譯Java代碼:將Java對象和方法調用轉換爲Clojure代碼

object1.object2(some_args).object3.object4(some_other_args).object5.objectnth.method(arg‌​1, arg2, argn); 

to Clojure?鏈中的一些對象可能是靜態類,靜態方法或類變量,其中一些是接口。這似乎並不簡單。例如,圖形庫中的對象。我記得有一次我試圖創建一個對象(Graphics),Clojure說它不知道那個類的Graphics。

非常感謝!

lisprog

+2

你有具體的例子嗎?上面的示例有點含糊。舉個例子,你可以先看http://clojuredocs.org/clojure.core/doto。另請參閱http://clojure-doc.org/articles/language/interop.html –

+0

「鏈中的一些對象可能是靜態類」[編號](http://stackoverflow.com/q/1215881/ 5044950) –

+0

@AlanThompson實際上,['..'](https://clojuredocs.org/clojure.core/_ ..)在這種情況下更合適。 –

回答

1

讓我們的Java示例:

public class Test { 

    public Test a; 

    public Test getA() { 
     return this.a; 
    } 

    public Test add(Test a) { 
     this.a = a; 
     return this; 
    } 

    public int foo(int a, int b, int c) { 
     return a+b+c; 
    } 

    public long foovar(Long... ai) { 
     long r = 0; 
     for (long i:ai) r+= i; 
     return r; 
    } 
} 

,並顯示出一堆的方式訪問內部對象:

(import 'Test) 

;; create all the objects 
(def t1 (Test.)) 
(def t2 (Test.)) 
(def t3 (Test.)) 
(def t4 (Test.)) 
(def t5 (Test.)) 
(def t6 (Test.)) 

;; and lets chain them together: 
(.add t1 (.add t2 (.add t3 (.add t4 (.add t5 t6))))) 

;; verify using member access: 
(= t6 (.. t1 a a a a a)) ;; true 

;; verify using method call: 
(= t6 (.. t1 getA getA getA getA getA)) ;; true 

;; and mixed access 
(= t6 (.. t1 a a getA a a)) ;; true 

;; lets invoke foo: 
(.. t1 getA getA getA getA getA (foo 1 2 3)) ;; 6 

;; and invoke foovar: 
(.. t1 getA getA getA getA getA (foovar (into-array[1 2 3]))) ;; 6 

現在,我們還可以創建輔助功能:

;; get the object at depth n using functions 
(defn get-nth-function [o n] 
    (first (drop n (iterate (memfn getA) o)))) 

;; get the object at depth n using member access. 
;; This same notation could also be used for function, 
;; however I just wanted to show an example of memfn 
(defn get-nth-member [o n] 
    (first (drop n (iterate #(.a %) o)))) 

;; lets verify: 
(= t6 (get-nth-member t1 5)) ;; true 

;; lets invoke foovar on object position 6, 
;; on a range of numbers from 1 to 10 
(.foovar (get-nth t1 5) (into-array (range 10))) ;; 45 

這應該顯示clojure和java之間交互的靈活性。當你有靜態成員時,你可以像System/out那樣通過/來訪問它們(儘管.也可以)。請務必完整閱讀http://clojure-doc.org/articles/language/interop.html,如果您還沒有收到任何東西,請告訴我們。

+1

非常感謝你!相信我;我已經多次從clojure官方網站上閱讀過java-clojure interop。我很高興能從你這樣的人那裏得到一些慷慨解答知識的答案,而不僅僅是告訴我RTFM。再次感謝 ! – lisprogtor