現在のディレクトリでプログラムを実行する前に `。/`を入力する必要があるのはなぜですか?


92

a.outUbuntuターミナルを使用してCプログラムを実行しているときに、単に書くのではなく、常に./前に入力する必要があるのはなぜですか?これに対する解決策はありますか?a.outa.out




回答:


119

a.outシステムなどのプログラムの名前を入力すると、PATHでファイルが検索されます。私のシステムでは、PATHは

/usr/lib/lightdm/lightdm:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games

あなたもおそらく似ています。確認するにecho $PATHは、ターミナルに入力します。

システムは指定された順序でこれらのディレクトリを調べ、プログラムが見つからない場合はcommand not foundエラーを生成します。

コマンドの前に./「PATHを忘れて、現在のディレクトリだけを見てほしい」と効果的に言います。

同様に、次のような相対パスまたは絶対パスをコマンドの前に付けることにより、システムに別の特定の場所のみを調べるように指示できます。

../は、親ディレクトリ内を意味し../helloます。たとえば、親ディレクトリでhelloを探します。

./Debug/hello: " hello現在のディレクトリのDebugサブディレクトリを探します。"

または/bin/ls:「lsディレクトリを検索する/bin

既定では、現在のディレクトリはセキュリティリスクと見なされるため、パスにありません。Why isを参照してくださいデフォルトではパスにありませんか?理由はスーパーユーザーです。

現在のディレクトリをPATHに追加することは可能ですが、リンクされた質問に記載されている理由により、お勧めしません。


25
この。+1 この回答に記載されているセキュリティリスクのため、(現在の他の2つの回答が示唆しているように)自分に追加しないでください.PATH

8
また、特別な意味がないことは注目に値するかもしれ.ここでは、あなたが実行ファイルなどへの完全なパスまたは相対パスを使用することができます/home/user/foo/a.out./build/a.out
tobyodavies

@tobyodavies; 実際.に特別なのは、「私の現在のディレクトリ」を意味するため、ユーザーが読み取りおよび実行の特権で自分自身を見つける任意のディレクトリになる可能性があるためです。これは、特定の完全修飾パスを追加するよりも潜在的に危険です。
ウォーレンヒル

@WarrenHillをパスに追加することを検討するとき、はい、まったく異なります。しかし、bashの構文の観点から、.特別な地位を保持していない、それだけで、同様に始めることができるだけのパスだ/./blah全く同様に動作しますcatgrepbashプロンプトとして。
-tobyodavies

@tobyodavies:OK回答を編集して、あなたのポイントを含めました。
ウォーレンヒル

24

その理由は簡単です。

現在のディレクトリにあるアプリケーションと同じ名前のコマンドがあるとします。次に、シェルでコマンドを実行すると、組み込みコマンドの代わりにアプリが呼び出されます。他に何もなければ、これはセキュリティ上の懸念になります。

./シェルは、前で使用することを要求することで、その名前の組み込みコマンドではなく、指定された名前でアプリケーションを実行することを認識します。


1
あなたの説明は誤解を招くものです。シェルの組み込みコマンドと、PATH変数を介してアクセス可能な実行可能ファイルには違いがあります。実際のところ、あなたの答えは、私が読むほど、より不正確に感じます。
アーメドマスード

16

./にないファイルを実行します$PATH。むしろ、現在のディレクトリ(または別の経由./home/stefano/script.sh)でファイルを実行します。現在、PATHは、bashが実行可能プログラムを探すことができるすべての場所を含む環境変数であり、それらへの完全な(絶対)パスはありません。

この分離は、間違ったファイルの実行を避けるために必要です。つまりls、ホームディレクトリで呼び出されるファイルがある場合、PATHにないため、bashが本物と混同するのを防ぎますls。PATH変数は、検索順序も定義します。

  • コマンドを実行するか、プログラムがexecsyscall(カーネルの特別な方法、プログラムの起動方法)を作成しようとすると、システムはPATH内の各ディレクトリを通過してファイルを探します。プログラムが見つかると、複数のディレクトリにある場合でも、検索は中断され、最初に見つかったものが実行されます。

ファイルを実行するには、アクセス許可に実行可能ビットを設定する必要があります。

  • すでにコマンドラインを使用しているので、単に入力できますchmod +x finename

  • または、ファイルを右クリックして[ プロパティ ]を選択して、アクセス許可を設定できます

    代替テキスト

これで、ファイルをPATH内の任意のディレクトリにコピーして、どのディレクトリがそこにあるのかを確認できます(ユーザーごとに設定されています)echo $PATH

stefano@3000-G530:~$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games

実行可能ファイルを作成しcat、に移動すると/usr/local/sbin、にある適切なの代わりに実行さcat/binます。type catおよびを使用して、ファイルの場所を確認できますwhereis cat


2
注意すべき点が1つあります。彼の質問は、彼が何かをコンパイルしてリンクしgcc、自動的に実行ビットを設定したことを示しているようです。
ネイサンオスマン

12

./プログラムを実行する前に入力する必要があるのはなぜですか?

ターミナルでは、アプリケーションの名前を入力するたびに、たとえばgedit、ターミナルはアプリケーション(アプリケーションのバイナリー)を含むいくつかの(事前定義された)ディレクトリーを調べます。これらのディレクトリの名前はと呼ばれる変数に含まれていますPATH。を実行すると、この変数の内容を確認できますecho $PATH:?で区切られたディレクトリを参照してください これらの端末はあなただけ入力すると、検索対象になりますディレクトリですgeditnautilusまたはa.out。ご覧のとおり、a.outプログラムのパスはありません。すると./a.out、端末に「現在のディレクトリを見て、実行してa.out、見てはいけない」と伝えますPATH

解決策1

./毎回入力したくない場合は、にa.outディレクトリを追加する必要があります$PATH。次の手順でa.out/path/to/programs/、へのパスがであると想定していますが、実際のパスに変更する必要があります。

  1. ファイルの最後に次の行を追加するだけです~/.pam_environment

    PATH DEFAULT=${PATH}:/path/to/programs

    ソース:永続的な環境変数

  2. ログアウトして再度ログインします。これで実行することができますa.outせずに./任意のディレクトリから。

他のディレクトリに他のプログラムがある場合は、それらを上記の行に追加するだけです。ただし、たとえば「myPrograms」というディレクトリを1つ作成し、すべてのプログラムをその下に配置することをお勧めします。

解決策2

注:userName実際のUbuntuユーザー名に変更します。

実行したい他のプログラムがある場合はどうなりますか?そして、それらはすべて異なるフォルダーにありますか?「組織化された」解決策はbin、ホームディレクトリの下に呼び出されるフォルダーを作成し、そのフォルダーの下にシンボリックリンク(ショートカット)を追加することです。方法は次のとおりです。

  1. mkdir /home/userName/bin

    • これにより、binホームディレクトリの下にフォルダが作成されます。
  2. ln -s /path/to/programs/a.out /home/userName/bin

    • これにより、a.outプログラムの「シンボリックリンク」(基本的にショートカット)が作成されbinます。
  3. ログアウトして再度ログインします。これで実行することができますa.outせずに./任意のディレクトリから。

ここで、他の場所に別のプログラムがあるときはいつでもb.in、デスクトップ上のプログラムを言うと、あなたがする必要があるのは次だけです:ln -s /home/userName/Desktop/b.in /home/userName/binそして、あなたはそれなしでそれを実行することもでき./ます。

注: @Joe のコメントのおかげで、バックアップを行うとき、シンボリックリンクは特別に処理する必要があります。デフォルトでrsyncは、それらはまったく処理されません。そのため、復元するとき、それらは存在しません。


1
控えめに使用する場合、これは便利なトリックです。これを頻繁に使用すると、システムが他の誰かが予期しないことを行うようになります。また、バックアップを行うとき、シンボリックリンクは特別に処理する必要があります。デフォルトでは、rsyncはそれらをまったく処理しないため、復元するとそこにありません。
ジョー

1

Georgeが答えで指摘したように、これは現在の作業ディレクトリ()でファイルを実行していることに注意するのに役立ちますpwd

私はずっと前に先輩にこの質問をしたことを覚えています。彼は.、パスを追加してa.out、実行時に現在のディレクトリを検索して実行する必要があると言いました。この場合、私はする必要はありません./a.out

しかし、個人的には、これに反対することをお勧めします。それは私には決して起こりませんでしたが、異星人のネットワークディレクトリなどにいて、lsそこに悪意のある実行可能ファイルが存在する場合、.パスに含めることは非常に悪い考えです。この問題に頻繁に遭遇するというわけではありません。



3
私は完全に追加しないと同意.します$PATH。非常に危険なアイデア。
ネイサンオスマン

1

他の答えに加えて、ここでman bashそれをよく説明する重要な部分:

コマンド実行
       コマンドが単語に分割された後、結果が単純な場合
       コマンドとオプションの引数リスト、次のアクションは
       取られた。

       コマンド名にスラッシュが含まれていない場合、シェルは検索しようとします
       それ。その名前のシェル関数が存在する場合、その関数は
       上記の機能の説明に従って呼び出されます。名前が一致しない場合
       関数、シェルはシェル組み込みのリストでそれを検索します。もし
       一致が見つかった場合、そのビルトインが呼び出されます。

       名前がシェル関数でも組み込み関数でもなく、
       スラッシュ、bashはディレクトリの各要素のPATH
       その名前で実行可能ファイルを保持します。

0

「./」は、特定のプログラム(たとえば、独自のプログラム)を実行する場合に意味があります。このプログラムは、現在のディレクトリに存在する必要があります。「./」は、$ PATHのどこかにある標準コマンドを実行する場合は意味がありません。コマンド「実行するコマンド」は、実行するコマンドが$ PATHのどこにあるかを示します。


0
$ gcc hello.c -o /path/to/someplace/hello

ある場所に実行ファイルを生成します。その場所がパス上にある場合、ファイルを実行できます。「gccを使用してこのソースコードをコンパイルし、パス上のある場所に実行可能ファイルを配置する」アクションのラベルを作成する場合は、これをスクリプト化できます。

「testbin」などの新しいディレクトリを作成して、既存のパスディレクトリをクリーンに保つためにパスに配置することをお勧めします。


0

./パスの不要な検索を排除します。./現在のディレクトリのみを強制的に検索します。我々は与えていない場合./、それはのようなシステムに設定された各種のパスを検索します/usr/bin/usr/sbin/など


0

「./」は、現在のディレクトリにあるファイルを実行することを意味します。たとえば、パス全体を入力するショートカットです。

[root@server ~]#/path/to/file/file.pl

と同じです:

[root@server file]#./file.pl

前の例では、ディレクトリとそのsupディレクトリをファイルの場所に移動し、「./」を使用して現在のディレクトリでファイルを実行しました。

[root @ server〜]#/ path / to / file / file.pl」の前のファイルも、ファイルの場所まで「cd」するのが面倒ならファイルを実行します。


-4

非常にシンプルで、多くの用途があります。

  1. 同じアプリケーションの複数のバージョンがインストールされている場合、異なるパスで使用できますが、バイナリへのソフトリンクはで作成できます/usr/bin。たとえば、Python 2.7、Python 2.6はインストールされていますが、/ usr / bin / python-> python2.7 / usr / local / bin / python-> python2.6

パスにい/usr/local/binてPythonを実行すると、常にPython 2.7が実行されます。指定.すると、現在のフォルダーの実行可能ファイルが使用されます。

  1. .-常に現在のディレクトリからの実行を表します。そして、..常に前のディレクトリから実行することを意味します。
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.