私の最初の質問は-
class Explain() {
public Explain() {
}
}
コンストラクタは常にパブリックとして宣言する必要がありますか?
private
コンストラクターを作成するとどうなりますか。
コンストラクターが暗黙的にpublic
であるのを見てきました。では、なぜprivate
コンストラクターが便利なのでしょうか?または、まったく役に立ちません。誰もそれを呼び出せないか、オブジェクトを作成できない(private
コンストラクターのため)!それが私の2番目の質問です。
いいえ、Constructorsはpublic
、private
、protected
、またはdefault
にできます(アクセス修飾子はまったくありません)。
private
を作成しても、だれもアクセスできないわけではありません。クラス外の誰もアクセスできないことを意味します。したがって、private
コンストラクタも便利です。
private
コンストラクターの使用の1つは、シングルトンクラスを提供することです。シングルトンクラスは、オブジェクトの作成数を1つに制限するクラスです。 private
コンストラクターを使用すると、一度に複数のオブジェクトを作成できないようにすることができます。
例-
public class Database {
private static Database singleObject;
private int record;
private String name;
private Database(String n) {
name = n;
record = 0;
}
public static synchronized Database getInstance(String n) {
if (singleObject == null) {
singleObject = new Database(n);
}
return singleObject;
}
public void doSomething() {
System.out.println("Hello StackOverflow.");
}
public String getName() {
return name;
}
}
に関する詳細情報 アクセス修飾子
はい、コンストラクタは任意のアクセス指定子/アクセス修飾子を持つことができます。
プライベートコンストラクターは、singleton
クラスの作成に役立ちます。
シングルトン-シングルトンクラスは、実行時に(JVMごとに)単一のオブジェクトのみを作成できるクラスです。
シングルトンクラスの簡単な例は-
class Ex {
private static Ex instance;
int a;
private Ex() {
a = 10;
}
public static Ex getInstance() {
if(instance == null) {
instance = new Ex();
}
return instance;
}
}
上記のクラスの場合、オブジェクト(このクラス外)を取得する唯一の方法はgetInstance()関数を呼び出すことです。これは単一のインスタンスのみを作成し、それを返し続けます。
また、これはスレッドセーフではないことに注意してください。
コンストラクタは、パブリック、デフォルト、プライベートのいずれでもかまいませんが、すべてはコンストラクタで何をしたいかによって異なります。
たとえば、シングルトンクラスを定義している場合は、hideをお勧めします(プライベートにすると、クラスでのみ使用できるようになります)属する)他のクラスが自分の意志でクラスをインスタンス化するのを防ぐコンストラクタ。
同じパッケージ内のテストケースがアクセスできるように、テスト目的でデフォルトとして宣言することができます。
より詳細な情報が見つかりました こちら
コンストラクタがパブリックであるというルールはありません。一般に、他のクラスからもインスタンス化したいという理由だけで、パブリックとして定義します。
プライベートコンストラクターとは、「私以外の誰にもインスタンスを作成させない」という意味です。そのため、通常、シングルトンパターンが必要なときにこれを行います。
以下は、プライベートコンストラクターを使用するJDKのクラスです。
public class Runtime {
private static Runtime currentRuntime = new Runtime();
public static Runtime getRuntime() {
return currentRuntime;
}
// Don't let anyone else instantiate this class
private Runtime() {
}
}
いいえ、コンストラクタはプライベートを含む任意のアクセス修飾子を使用できます。 (プライベートコンストラクターは、クラス自体内のコードのみがそのタイプのオブジェクトをインスタンス化できることを意味するため、プライベートコンストラクタークラスがクラスのインスタンスの使用を許可する場合、クラスは、クラス内から作成されたインスタンス。)
例
class Alpha {
static String s = " ";
protected Alpha() { s += "alpha "; }
}
class SubAlpha extends Alpha {
private SubAlpha() { s += "sub "; }
}
public class SubSubAlpha extends Alpha {
private SubSubAlpha() { s += "subsub "; }
public static void main(String[] args) {
new SubSubAlpha();
System.out.println(s);
}
}
上記のプログラムの出力は
アルファサブサブ
コンストラクターは、あらゆる種類のアクセス修飾子を持つことができます。コンストラクターでの異なるアクセス修飾子の使用法は異なります。
どこからでもクラスをインスタンス化する場合は、コンストラクターpublic
を作成します。
クラスを継承し、その継承クラスをインスタンス化する場合は、コンストラクターprotected
を作成します。
通常は静的ブロックまたは静的メソッドである独自のメンバーからクラスをインスタンス化する場合は、コンストラクターprivate
を作成します。つまり、クラスのインスタンス化を制御し、インスタンス化に何らかのルールを適用します。プライベートコンストラクターの使用例は、シングルトンデザインパターンです。
シングルトンはプライベートコンストラクターを持つクラスの良い例であるという以前の回答に同意します。私は別の実装を推奨します:スレッドセーフシングルトン:
/**
* Thread safe singleton
*/
public class Singleton {
private static volatile Singleton instance = null;
/**
* Private constructor
*/
private Singleton() {
}
/**
* Gets the Instance of the Singleton in a thread safe way.
* @return
*/
public static Singleton getInstance() {
if (instance == null) {
synchronized (Singleton.class) {
if (instance == null) {
instance = new Singleton();
}
}
}
return instance;
}
}
スレッドセーフな方法でシングルトンを使用すると、並列コードの多くの痛みを防ぐことができます。
コンストラクタhasは、たとえば、次のようなカスタムファクトリクラスの作成中に、少なくとも保護され、さらにはプライベートになります。
public final class MyFactory {
private MyFactory(){} // this one prevents instances of your factory
}
public static void doSomething(){} // access that with MyFactory.doSomething
これは、コンストラクターをパブリックにしない場合を示す1つの例にすぎないことに注意してください。
他の人は、コンストラクタにはアクセス修飾子があるかもしれないと指摘しています。まだ言及されていない側面は、コンストラクターの側面修飾子が構築の2つのまったく異なる側面を制御しますが、それらを個別に制御することは許可しないということです。
ClassName
のインスタンスのインスタンスを作成できるユーザーと、使用できるコンストラクター。ClassName
のextensionsを作成でき、どのコンストラクタを使用できるか。両方のJavaと.NETでは、これら2つの質問に対する答えが一緒になっている必要があります;クラスがfinal
(またはsealed
)ではなく、コンストラクターを許可する場合新しいインスタンスを作成するために外部コードによって使用される場合、外部コードは派生型を作成するために同じコンストラクターを使用する自由もあります。
多くの場合、クラスがパッケージプライベート(internal
)コンストラクターのみを持ち、新しいインスタンスを返すパブリックメソッドを公開することが適切な場合があります。そのようなアプローチは、String
のようなタイプをゼロから設計している場合に使用できます。 String
を含むパッケージはそれを抽象型として定義できますが、コンテンツを_UCS16String
_および_byte[]
_として保存するAsciiString
や_Char[]
_などの具象派生型を含めることができます。それぞれ; String
を返すメソッドは、文字列にASCIIの範囲外の文字が含まれているかどうかによって異なります。String
も派生型もコンストラクタを公開しない場合、パッケージ外で、パッケージ内のすべての派生型が文字列として動作することが期待される場合、String
型の参照を受け取るコードは、文字列として正常に動作することを期待できます(たとえば、ただし、パッケージの外部でコンストラクタを公開すると、派生型が奇妙で奇妙な動作をすることが可能になります(たとえば、検証および検証後に内容を変更するなど)。
構文の観点から、Fnord foo = new Fnord(123);
と言うことができることはFnord foo = Fnord.Create(123);
と言うよりも少しいいですが、後者の構文を必要とするクラスFnord
ははるかに優れた制御を維持できます。オブジェクト作成プロセスで。
これらの回答のほとんどは、シングルトンまたはファクトリクラスを参照しています。 (たとえば) Java.lang.Math class にプライベートコンストラクターが表示される場合、すべてが静的であり、誰もコンストラクター(クラス自体を含む)を呼び出すべきではありません。プライベートコンストラクターを持つことにより、クラス外のユーザーがコンストラクターを呼び出さないようにします。 (これは、クラス内の誰かがコンストラクターを呼び出すことを妨げるものではありませんが、その後、独自のルールを破っています。)
簡単な説明は、クラスにコンストラクターがない場合、コンパイラーは自動的にデフォルトのコンストラクターを作成します。
コンストラクターは常にパブリックとして宣言されるわけではなく、プライベート、保護、またはデフォルトにすることもできます。
プライベートコンストラクターは、クラスが呼び出し側によって完全かつ明確に表現/表現されるのを防ぎます。その場合、プライベートコンストラクターが便利です。クラスをサブクラス化する必要がない場合は、プライベートコンストラクターを使用できます。