2011-01-02 33 views
13

Tôi đã tạo ra một kỷ lục như thế này:Không thể nhập hồ sơ clojure

(defrecord User [user-id email]) 

: nhưng khi tôi cố gắng để truy cập nó từ một tên không gian tôi nhận được lỗi:

(User. "name" "email") 

java .lang.IllegalArgumentException: không thể giải quyết classname: người dùng

Nó hoạt động khi tôi làm:

(oe.model.modelcore.User. "name" "email") 

: Tôi biết tôi sẽ cần phải nhập khẩu các lớp Java, nhưng là có cách nào cho clojure để làm điều này tự động khi tôi làm:

(use 'oe.model.modelcore :reload) 

Trả lời

13

Về mặt kỹ thuật, bạn phải yêu cầu nó (không nhất thiết phải sử dụng nó) sao cho tệp chứa định nghĩa bản ghi được biên dịch và lớp được tạo. Sau đó, bạn phải nhập nó để nó có sẵn để xây dựng như một lớp Java. Nếu bạn tạo hàm khởi tạo trong các ns đầu tiên như

(defn new-user [id email] 
    (User. id email)) 

thì bạn sẽ không cần phải nhập nó trong ns gọi.

tôi đã viết này lên một thời gian trở lại đây:

+3

Rất may, đó là không cần thiết nữa bắt đầu với Clojure 1.3, nơi ghi lại trở thành công dân hạng nhất. Chỉ muốn để lại một bình luận cho những người đọc điều này ngay bây giờ. –

+0

Từ kinh nghiệm của tôi, bạn cần phải biên dịch AOT, và cả hai yêu cầu và nhập khẩu hồ sơ. (Tất nhiên chúng tôi đã sử dụng thư viện lược đồ lăng trụ để xác nhận hồ sơ của chúng tôi) –

9

Bạn phải nhập khẩu kỷ lục như thế này:

(ns some-ns 
    (:import [oe.model.modelcore User])) 
+0

Tôi đã thay đổi câu trả lời chấp nhận này vì đây là câu trả lời mà làm việc cho tôi trong tháng 1 2014 – Zubair

8

Trong câu hỏi của bạn, bạn đang tạo ra một kỷ lục, sau đó gọi các nhà xây dựng cho lớp được tạo ra như một tác dụng phụ. Để làm như vậy, bạn cần nhập khẩu lớp đó như đã đề cập trong câu trả lời khác.

Tuy nhiên, imho đường dẫn ưu tiên (kể từ Clojure 1.4) là sử dụng các hàm dựng được tạo bởi defrecord (ở đây chúng sẽ có tên là ->Usermap->User). Các hàm này cho phép bạn tránh các biểu mẫu interop và chỉ tham chiếu đến các hàm xây dựng giống như bất kỳ hàm nào khác. Bằng cách tránh interop, đây là một giải pháp ít hosty di động hơn:

(ns some-ns 
    (:require [oe.model.modelcore :refer (->User)])) 

(def user (->User "name" "email")) 
7

Nó có thể được thực sự khó khăn nếu bạn có - (gạch ngang) trong không gian tên của bạn.

As it turns out there were two errors:

– Importing defrecord from another namespace is not just :use. I had to first :require the namespace, then import the defrecord. This was a trivial problem to solve and I figured it out quickly. Only this did not work in my case

– Dashes “-” and Underscores “_” are a nuisance since we are mixing Lisp with Java. While the file system uses underscores Clojure converts things to dashes. Brilliant.

So to fix the second error I use the follow in the ns block

(ns adder.core 
    (:require building-blocks.activity) 
    (:import [building_blocks.activity Activity])) 

https://cyrax.wordpress.com/2013/07/22/clojure-importrequireuse-defrecord-from-another-namespace/

+1

+1 Vấn đề gạch dưới trong: nhập là những gì vẫn còn cắn tôi, vì vậy cảm ơn bạn đã thêm điều này lâu sau khi OP chấp nhận câu trả lời. –

+0

Xin lỗi vì sự sụt giảm, đó là do nhầm lẫn và tôi không thể lấy lại được! – Aspasia

+0

Bấm lên phiếu bầu :) – MAGx2

Các vấn đề liên quan