問題タブ [gen-class]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
java - clojure から gen クラスのメソッドを呼び出す方法
gen-class を使用して、Clojure コードから Java クラスを生成しています。gen-class を機能させるには、クラスに追加されるすべてのメソッドに最初のパラメーターを追加する必要があります (ここでは と呼びますthis
)。
コンパイル後、Java コンテキストでメソッドを呼び出すと正常に動作します。
しかし、Clojure から直接起動するにはどうすればよいでしょうか?
最初のパラメーターが欠落しているため、次のことは機能しません。
空の最初のパラメーターで関数を呼び出すのは良い習慣ですか?
または、addToString
内部で使用する関数 (例: ) を追加し、メソッドとしてクラス ファイルに追加される関数からこの関数を呼び出す必要がありますか?
clojure - Leiningen が私の :gen-class を常に適切に使用できないのはなぜですか?
新しい Leiningen プロジェクト ( ) を作成し、 を使用するlein new app example
コードを追加するとします。example/src/example/core.clj
:gen-class
次に JAR ( lein uberjar
) を作成して実行すると、すべて正常に動作します。ただし、アプリを直接実行しようとすると ( lein run
) ClassNotFoundException
、. さらに、REPL ( lein repl
) を開くと、最初は以前と同じエラーが発生しますが、次のコードを実行すると、次のようになります。
lein run
または にエラーが表示されなくなりましたlein repl
。
ここで正確に何が起こっているのか、REPL からコードを手動でコンパイルすることなくアプリを直接実行する方法を教えてください。
編集:もう少し浮気した後、この問題の解決策は追加することであることがわかりました
にproject.clj
。(@Marsに感謝します!)ただし、以前に単純に削除しようとしたため、まだ混乱しています( docs^:skip-aot
によると)動作するはずです:
これはデフォルトで AOT コンパイルされます。
^:skip-aot
これを無効にするには、メタデータを名前空間シンボルに添付 します。
しかし、そうではありません。なんで?
別の編集(これを別の質問に分割する必要がある場合は、お知らせください。そうします):ハイフン(lein new app my-example
)で遊んでいて、奇妙なことが起こっています。これは機能しません:
しかし、これは:
私のクラス名は、小文字 ( example.core
) で始まるか、ハイフン ( my-example.Core
) を含むことができますが、両方を含むことはできませんか? 私は本当にそれを取得しません。
そして最後に、lein uberjar
その最後の例 (明示的な:name
)で失敗します。
私が知る限り、それを修正する唯一の方法は、Application
サブクラスを別の名前空間に分割することです。別の方法はありますか?
java - オーバーロードおよびオーバーライドされたメソッドの Clojure gen-class
clojureでこのクラスのメソッドgen-class
をオーバーライドするために使用しようとしています。複雑なのは、このメソッドが 3 回オーバーロードされているという事実から来ています。compare(WriteableComparable a, WriteableComparable b)
int compare(WritableComparable a, WritableComparable b)
int compare(Object a, Object b)
int compare(byte[] b1, int s1, int l1, byte[] b2, int s2, int l2)
これまでのところ、私の試みは次のようになります。
compare(Object a, Object b)
すべてがコンパイルされますが、実行すると null ポインター例外が発生します。これは、間違ったメソッド (つまり、意図した の代わりに)をオーバーライドしたためだと思われcompare(WritableComparable a, WritableComparable b)
ます。参考までに、 のObject
バージョン から バージョン までをcompare
呼び出しますWriteableComparable
。
NPE が別のものから来ている可能性は十分にありますが、少なくともこの clojure コードに絞り込みました (対応する Java バージョンで実行すると、問題なく動作します)。
メソッドのどのオーバーロードされたバージョンを使用するかを指定する方法はありますか?
:methods
(呼び出しに句を追加しようとしましたgen-class
が、スーパークラス メソッドではなく、新しいメソッドのみを宣言する必要があることを学びました。)
clojure - 実行時にclojureでJavaクラスを定義してインスタンス化するにはどうすればよいですか
gen-and-load-class
fromを使用してからclojure.core
カスタムクラスローダーを使用しdefineClass
て、生成されたバイトコードで呼び出しようとしましたが、呼び出すと
私は得ています
アップデート:
だから私は @Elogent によって提案されたように deftype を使用しました:
私がしたときのAOTの後、私はjavap Foo.class
得ました:
これはまさに私が必要とするものです。ありがとう@Elogent!
clojure - コンパイルと gen-class に関する Clojure.org ドキュメント
コンパイルに関する clojure.orgのドキュメント、最後の部分の gen-class の例を読んでいます。私は例を実行し、それを Java アプリとして実行しようとすると:
java -cp ./classes:clojure.jar clojure.examples.hello Fred
端末で : を取得しますError: Could not find or load main class clojure.examples.hello
。誰か助けてくれませんか?だれかが gen-class と :gen-class について学ぶ場所を紹介できますか? Web 上にはあまりドキュメントがありません。
unit-testing - boot-clj: gen-class で生成されたクラスの単体テストをビルド/起動する方法
私の clojure プロジェクトでは、gen-classコマンドを使用していくつかの Java クラスを作成しました。彼らは[extractor.yaml YAMLExtractor YAMLExtractorFactory]
です。これらのクラスに対して単体テストをビルドしたかったのですが、java.lang.ClassNotFoundException: extractor.yaml.YAMLExtractor
テストを実行するとエラーが発生しました。
エラーの原因となるファイル: yaml_extrator_factory.clj
エラーは、テスト中にのみ発生します。プロジェクト全体がエラーなしで AOT コンパイル可能であり、jar ファイルをビルドしても問題ありません。
テストsimple.cljには head が含まれています:
そして、どのクラスが CLASSPATH を出力するかをテストします。yaml-extractor-factory
使用されませんでした。テストは次のコマンドで実行されます:
boot aot -a update-classpath run-test -t extractor.simple
ここで、タスクupdate-classpathがクラスパスに追加(get-env :directories)
され、run-testがテストを実行します。run-test
通常の clojure コードで問題なく動作します。
run-testは、次の内容の私のタスクです。