web-dev-qa-db-ja.com

Javaがファイル名を引数に入れないのはなぜですか?

CおよびC++では、mainメソッドは、argv [0]にある配列の最初の位置にファイル名を保持します。ただし、Javaでは、ファイル名はargs文字列配列に含まれません。

これには実際的な理由はありますか?これにより、コマンドライン引数の反復が1ベースではなく0ベースになることがわかりますが、メリットはありますか?ファイル名は役に立たないと見なされただけですか?

21
Jordan L

場合によっては、プログラムをさまざまな方法で実行し、その呼び出し方法でさまざまな動作を示すことができます。 vimviとして呼び出すと、互換モードで実行されます。時には、いくつかの関連プログラムの1つのバージョンを維持しようとすることがあります。たとえば、多くのUNIXシステムのmailqnewaliasessendmailへのリンクであり、これらのプログラムは同期を維持します)


Javaプログラムは通常、次のように呼び出されます。

%Java -jar foo.jar args 
%Java Foo args 

最初のバージョンは、メインクラスを示すマ​​ニフェストファイルがある場所です。2番目のバージョンは、クラスパスで見つかったクラスFooでmainメソッドを実行します。

Javaに対して提示される情報は、jarへのパスまたは呼び出されるクラスの名前のいずれかです。

Jarの場所は、コードを作成するのに十分重要ではありません(実際には元の仕様の一部ではありませんでした)。 jarは実際には任意の名前を付けることができ、多くの場合バージョン番号が含まれます。さらに、クラスが.jarに格納されていたという保証はありません(抽出された可能性もあります)。

Java _-jar_を使用したアプリケーションの呼び出しには、マニフェストで定義されているクラスを入力する方法が1つしかありません。実行できる名前の変更はありません。

クラス名を指定して呼び出す別のオプションは、実行ユニットを直接指します。さらに、multiplyという名前を付けることはできません。_Bar.class_を_class Foo_のコードにすることはできません。この方法では機能しません。

これは、Cの意味で_argv[0]_の情報をJavaアプリケーションに渡すことにはまったく意味がないことを示しているはずです-そのどちらもJavaになり、無意味で任意、または呼び出されているクラスの名前(すでにコードを実行している(絶望的な場合はgetClass().getEnclosingClass().getName()のようなものを実行できます...))。

ここで重要なのは、.jar内のクラスまたはクラスパス上に複数のMainメソッドを定義できることです。そして、_argv[0]_が何であるかに基づいて一連のifステートメントがあるかのように、それらに異なる動作をさせることができます。

私は過去に、マニフェストで定義されたものではなくTestクラスのMainメソッドを呼び出す_Java -cp Foo.jar com.me.foo.Test_に似たコードを使用しました。

17
user40980