web-dev-qa-db-ja.com

main関数でargcとargvの名前を変更しても安全ですか?

多くのプログラムは、多くの引数と文字列の配列に標準名を使用します。メイン関数のプロトタイプはint main(int argc, char *argv[]);のようになります。しかし、これらの変数にカスタム名を選択すると、何かが壊れるでしょうか?

例えば。 int main(int n_of_args, char *args[]);

コンパイラのコンテキストでは、すべてが正常です。これらの変数はメイン関数に対してローカルであるため、任意の名前を付けることができます。そして、シンプルなコードは完璧に構築され実行されます。ただし、これらの名前はプリプロセッサで使用される場合があります。これらの引数の名前を変更しても安全ですか?

[〜#〜] ps [〜#〜]個人的には、これらの名前は非常に似ており、1文字だけ異なるため、これらの名前が悪いと感じています。しかし、誰もが何らかの理由でそれらを使用しています。

82
yanpas

はい、有効な変数名を使用している限り安全です。これらはローカル変数なので、スコープはmain関数を超えません。

C標準 のセクション5.1.2.2.1から:

プログラムの起動時に呼び出される関数は、mainという名前です。実装は、この関数のプロトタイプを宣言しません。 intの戻り値の型で、パラメータなしで定義されます:

int main(void) { /*  ... */ }

または、2つのパラメーター(ここではargcおよびargvと呼ばれますが、。ただし、名前は使用される関数に対してローカルであるため、任意の名前を使用できます。宣言済み):

int main(int argc, char *argv[]) { /* ...   */ }

または同等;または他の実装定義の方法で

そうは言っても、argcargv以外のものを使用すると、これらのパラメーターの従来の名前に慣れているコードを読んでいる他の人を混乱させる可能性があります。明快さの側で間違いを犯す方がいい。

119
dbush

argcおよびargvという名前は、実際にはC++ 11より前のC++標準で義務付けられていました。それは述べた:

すべての実装は、mainの以下の両方の定義を許可するものとします。

int main ()

そして

int main ( int argc , char * argv [])

そしてargcargvの要件について議論しました。

そのため技術的には、異なる名前を使用するプログラムは標準に準拠しておらず、コンパイラはそれを拒否することが許可されていました。もちろん、実際にそうしたコンパイラはありません。 comp.std.c ++のこのスレッド 、または このC++ 03ドラフト標準 のセクション3.6.1を参照してください。

これはほぼ間違いなく単なる見落としであり、C++ 11で変更されました。

すべての実装は両方を許可するものとします

  • intを返す()の関数
  • intcharへのポインターへのポインター)intを返す関数

main(8.3.5)のタイプとして。後者の形式では、説明の目的で、最初の関数パラメーターはargcと呼ばれ、2番目の関数パラメーターはargv、…と呼ばれます

38
Nick Matteo

これらのパラメータの名前を変更できます安全に好きなように

_ int main(int wrzlbrnft, char* _42[]) {
 }
_

名前は砂で書かれています。最終的にコンパイルされたコードには影響しません。


重要なのは、宣言と定義のパラメータータイプが実際に一致することだけです。

main()関数のシグネチャは、本質的に次のように宣言されます

_ int main(int, char*[]);
_

実際に実装で使用する必要がある場合は、名前を付ける必要があります。前述のように、どの名前が使用されるかは実際には関係ありません。

28

はい。それは安全で、奇妙に見えますが、何も壊しません。

15
coredump

はい、異なる名前を使用しても安全です。

個人的には、伝統的なargcargvはコードを扱うことのある他のすべてのCプログラマーに広く知られ、親しまれているのでお勧めしません。長い目で見れば、あなた自身の特別な異なる名前を使用すると、あなたの名前がより良いのであなたを救うよりもはるかに多くの混乱や欲求不満を読者にもたらします。

「ローマにいるときは、ローマ人と同じように。」

7
Steve Summit

はい、必要に応じて名前を変更できます。それらは単なる関数パラメーター名であり、それ以上のものではありません。

5
orbitcowboy

誰もが技術的なC++ルールを十分にカバーしていると感じています。答えはイエスです。伝統と、この1つの特定の機能が特別で象徴的であり、これに基づいて変更しない有効なポイントが含まれているという事実は無視しましょう。

多くの場合、選択肢の哲学はめったに議論されないと感じており、したがって、このことが最初に求められた理由にとって重要であると思うので、この問題についての視点を提供したいと思いました。

私へのこの質問は、一般的にコードで英語を表現する際の選択を伴います。特に、ショートハンドが似たようなテキストを見つけた場合、ショートハンドの説明に悩まされるようです。しかし、あなたの例では、argnをn_of_argsに変更しても、1つのタイプのショートハンドから別の形式のショートハンドへの変更のみが行われます。

単語「番号」は文字「n」に置き換えられました。

アンチショートハンドの哲学を介してショートハンド名を変更する場合、次のようなものがより適切に見えるかもしれません。

main(int argumentCount、char ** argumentVector)

私は常に二つのことを考えます:それらが何であるか、そして/またはそれらの暗黙の使用法によって物に名前を付ける。それを引数ベクトルと呼ぶことは私にとって冗長です。なぜなら、ベクトルであることの性質は二重間接参照によって暗示されているからです**。したがって、コードをどのように記述するかについてのより良い長所は、**引数です。

ArgumentCountという変数はintとして宣言され、Countを負にすることはできませんが、負のint {unsigned is better}を使用できます。

繰り返しになりますが、この解釈では、それが何であり、どのように使用されるかが示されます。カウントの場合、負になることはないと思います。結局のところ、どうすれば-2個のリンゴをカウントできますか。私は言う、あなたは2つのリンゴをOWE。数値の場合、負のケースが可能になると予想されます。これが、追加の「of」という言葉があなたにとって重要である理由です。それと、おそらくコレクションによって参照される数値は、コレクション自体のプロパティではなく、特定のアイテムを意味します。つまり、argumentsNumber = 5は、numberOfArgumentsではなく特定の引数を意味します。

main(int maxArgumentsIndex、char ** arguments)。

これにより、あいまいさがなくなります。それをインデックスと呼ぶことで、否定的なケースのあいまいさを取り除き、それが何であるかを説明し、さらにその使用方法を説明します。また、英語の言い回しでは、最大値は絶対値であり、この値を変更する奇妙なコードを記述します(constである必要があります)。ここでは、「引数」は複数形であり、それが何であり、どのように既に使用されるべきかを説明しているため、意味があります。 IndexがCount/NumberOfの-1であるため、この方法で解釈することさえ危険です。 5つの引数は4のmaxIndexを生成します!!

他の関数と私は完全に使用します:

void function(const unsigned int maxArgumentsIndex、const char ** arguments)

すべての状況が長文記述子に値するとは限りません。実際、特にVec3f、Matrix、Quaternionなどの数学クラスを作成する場合は、短い手で読むと読みやすさが向上する場合があります。 。 float x、y、z vrs。 float xComponentなど。

これはすべてスタイルの選択であると理解していますが、選択を意識することは長期的には本当に役立つでしょう。配列が複数形で書かれていない場合、熟練したプログラマーが悩まされることを保証しますが、メインは特別な存在の散文です;)

3
JMan Mousey

C標準に従って、はい、名前を変更できますが、影響はありません。私が理解したように、C言語では、デフォルトのキーワード/タイプ/トークン名は目的/使用法で定義されていたため、同じように名前が定義されています

argc --> argument count

argv --> argument vector

これは使用法の観点からも理にかなっているので、任意の名前に変更できますReserved names

GCCでは、プログラムの実行は関数名mainで始まりますが、パラメーターに依存しません。

マイクロコントローラー用のスタンドアロンプ​​ログラムを作成する場合、mainという名前を気にする必要はありません。代わりに、独自のnameを定義して、関数を指すようにAssembly entry_pointを変更できます。これは、コントローラーコンパイラーと事前定義されたコントローラーソースコードの可用性に依存します。私はこれをCode-warriorのFreescaleコントローラーで行いました。

私のメモ:

コードをより見やすく、読みやすくするために、共通の標準/コードスタイルに従うことをお勧めします

2
ntshetty

コンパイラに関する限り、安全です。

これが引き起こす唯一の問題は混乱です。コードを読む人は、これらの2つの変数に標準名が付いていることを期待します。次のようなこともできます:

int main(int foo, char ** bar)
{
    int argc;
    float argv;

しかし、これがいかに悪い習慣であるかを言う必要はないと思います。

0
klutt