default-packageのjava-classesにアクセスする方法は?


98

私は現在、他の人と一緒にgrailsプロジェクトで作業しています。私はいくつかのJavaクラスを書かなければなりません。しかし、groovyで作成された検索可能なオブジェクトにアクセスする必要があります。このオブジェクトはdefault-packageに配置する必要があるようです。

私の質問は:名前付きパッケージのJavaクラスからdefault-packageのこのオブジェクトにアクセスする方法はありますか?

回答:


129

名前付きパッケージのデフォルトパッケージのクラスは使用できません
技術的にはあなたのことができ、Shariqueアブドラさんのように答えリフレクションAPIを介して、しかし、無名の名前空間のクラスがある範囲内にない輸入申告

J2SE 1.4より前のバージョンでは、次のような構文を使用してデフォルトパッケージからクラスをインポートできました。

import Unfinished;

それはもはや許されない。したがって、パッケージ化されたクラス内からデフォルトのパッケージクラスにアクセスするには、デフォルトのパッケージクラスを独自のパッケージに移動する必要があります。

groovyによって生成されたソースにアクセスできる場合は、ファイルを専用パッケージに移動し、この「パッケージ」ディレクティブを最初に追加するために、いくつかの後処理が必要です。


2014年の更新:JDK7およびJDK8のバグ6975015には、名前のないパッケージからのインポートをさらに厳しく禁止することが記述されています。

TypeNameクラス型、インタフェース型、列挙型、または注釈型の正規の名前でなければなりません。
型は、名前付きパッケージのメンバーであるか、最も外側の字句的に囲む型が名前付きパッケージのメンバーである型のメンバーである必要があります。そうでない場合、コンパイル時エラーが発生します


アンドレアスはコメントで指摘している

「そもそも[デフォルトのパッケージ]があるのはなぜですか?設計エラーですか?」

いいえ、それは意図的です。
JLS 7.4.2。名前のないパッケージは言う:「名前のないパッケージは、主に小規模または一時的なアプリケーションを開発するとき、または開発を始めるときの便宜のために、Java SEプラットフォームによって提供されます」。


7
以前に他の人に説明したように、デフォルトのパッケージはJavaの世界では二流の市民です。それをしないでください。:-)
Chris Jester-Young、

1
(非常に時間の制約を受けたプロジェクトで)Groovyまたはdefault-packageのコードを学ぶ必要があるようです。:-(
Mnementh 2008年

11
@ ChrisJester-Youngもしそうなら、なぜそもそもなぜそこにあるのですか?設計エラー?
Pacerier、2011年

なぜ廃止されたのですか?
Suzan Cioc 2014年

@SuzanCiocの意味:「J2SE1.4の後で、デフォルトのパッケージにアクセスできなくなるのはなぜですか?」
VonC、2014年

61

実際、それは可能です。

リフレクションAPIを使用すると、これまでにどのクラスにもアクセスできます。少なくとも私は次のことができました:)

Class fooClass = Class.forName("FooBar");
Method fooMethod = fooClass.getMethod("fooMethod", String.class);

String fooReturned = (String)fooMethod.invoke(fooClass.newInstance(), "I did it");

Scalaのために、次のコードは動作します:val bar = "hi"; val fooClass = Class.forName("FooClass"); val fooMethod = fooClass.getMethod("foo", classOf[Array[String]]); val fooReturned = fooMethod.invoke(fooClass.newInstance(), Array(bar));
Jus12

2
すばらしい答え、+ 1。しかし、質問はかっこいいので、ダックタイピング(おそらくダクトテーピングのように)を使用できます...Class.forName("FooBar").newInstance().fooMethod("I did it")
Bill K

7

jarjarを使用して、次のルールでjarファイルを再パッケージします。

rule * <target package name>.@1

ソースjarファイルのデフォルトパッケージ内のすべてのクラスがターゲットパッケージに移動するため、アクセスできます。


4
jarjarの使用方法のデモはすばらしい
BiGGZ

@BiGGZ:README.mdを参照してください ant、gradle、またはコマンドラインでjarjarを使用する方法については、jarjar githubリポジトリファイルを参照してください。
Lucidiot 2017年

3

Groovyコード内でパッケージを使用でき、問題なく動作します。

最初はコードの小さな再編成とgrails-app最初は少し苦痛を意味するかもしれませんが、大規模なGrailsプロジェクトでは、物事をパッケージに編成することは理にかなっています。Java標準パッケージの命名規則を使用しますcom.foo.<app>.<package>

あなたが見つけているように、デフォルトのパッケージにすべてのものがあると、統合の妨げになります。

コントローラーは、Javaパッケージに入れられないようにする1つのGrailsアーティファクト(またはアーティファクト)のようです。たぶんConvention、まだそのことを理解していません。;-)


0

アイデアを完成させるためだけに:

default-package 内から、名前付きパッケージにあるオブジェクトにアクセスできます。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.