質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Q&A

解決済

4回答

1071閲覧

定数の定義より前にその定数を使う関数の定義を書いても大丈夫なのか

intron

総合スコア36

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

0グッド

0クリップ

投稿2017/04/25 14:11

下記のtest01.phpのように、定数の定義より前にその定数を使う関数の定義を書いてもきちんと定数の値が表示されました。
なぜ後で定義される定数を使っても大丈夫なのでしょうか。

test01.php

php

1function funcA() { print CONST_B . PHP_EOL; } 2 3define('CONST_B', '定数テスト'); 4 5funcA();

実行結果

text

1$ php -f test01.php 2定数テスト

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答4

0

ベストアンサー

function より define の方が先に処理されるからです。

投稿2017/04/25 14:23

Zuishin

総合スコア28656

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

intron

2017/04/25 15:00

PHPプログラムの中の定数、関数、クラスなどのいろいろな定義がある中で定数の定義が先に評価されるということでしょうか。PHPプログラムの実行時の評価の順序などについて言及したドキュメントなどがあれば教えていただきたいのですがご存知でしょうか。
Zuishin

2017/04/25 21:25

http://php.net/downloads.php PHP のソースをどうぞ。 私は読んでいませんので、評価が始まるのが全部の構文木が構築された後なのかどうかまでは知りません。 ただ、構文木の中に未定義のシンボルがあれば、少なくともそれが評価されるまではその木の評価はできません。
Zuishin

2017/04/25 21:48

通常、字句解析・構文解析・評価の順に処理が進みます。 次のように無限ループの後に間違った構文を書くと、ループが始まる前にエラーがでます。これはループ後の構文解析がループの評価より先に行われていることを意味します。 <?php while(true) print(1); helloworld しかし、次のようにループの後に未定義の関数を書くと、ループが始まります。 <?php while(true) print(1); helloworld(); これは評価がソースの前から行われていることを示します。 つまり、PHP の場合、評価は逐次実行されるが、評価が始まった時には木の構築は全て終わっていると推測されます。
Zuishin

2017/04/25 21:53 編集

つまり、function の評価が始まる時には define の構文木の構築は終わっており、いつでも評価できる状態にあると推測されます。
Zuishin

2017/04/25 21:54

実際にはソースを読んで確かめてください。
intron

2017/04/26 13:52

詳しく説明していただいてありがとうございます。
guest

0

プログラム実行時、最初にソースコード全体を解析されるということでしょうか?

現在のほとんどの言語はPHPも含め実行前にソースコード全体を解析しますが、それは必須では無いです。
冒頭から実行あるいは定義しながらソースを読んでいくPHP風な言語があったとしても、funcAの定義の中で、構文解析をすればCONST_Bは定数だと言うことは分かりますので、そのまま関数funcAが定義されます。

その次に、CONST_Adefineされます。

その次に、funcAを呼び出して、呼び出されたfuncAの中でようやくCONST_Bの価を参照しようとしてすでにdefineされているので値の取り出しに成功します。

つまりfuncAの定義時にはCONST_Aが定数だと言うことさえ分かれば良くて、値が入っている必要は無いです。値は参照するときに必要です。

CONST_AdefinefuncAの呼び出し順序を入れ替えると、funcAの実行時点で、CONST_Bは未定義で、普通の言語だとエラーになります。PHPの場合はその辺がいい加減なので、CONST_B"CONST_B"という文字列値を持っている事になりエラーにはなりません。ただし警告が出ますが。

投稿2017/04/25 15:50

otn

総合スコア84423

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

intron

2017/04/26 13:49

詳しく説明していただいてありがとうございます。
guest

0

単純に言うと、
define は読み込み時に評価され、
関数の中身は実行時に評価されるからさ!

本当はもっと複雑ですが……。

コンピュータ言語というのは、何段階かに分けて解釈し、徐々にマシン語に近づいていきます。
define は最初の方に解釈され、関数の中身は後の方に解釈されるので、大丈夫なのです。

投稿2017/04/25 14:57

morisoba

総合スコア90

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

なぜ後で定義される定数を使っても大丈夫なのでしょうか。

同じように、funcA の中で利用している別の funcB があったとして、その論でいくと funcA よりも先に funcB を定義する必要がありそうですね。

さらに funcB から別の関数 funcC が使用されていたら...

とまぁ、そんな感じで定義する順番を考えなければならないとすると、とてもプログラムを書くことはできなさそうですね。

投稿2017/04/25 14:46

koko_u

総合スコア936

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

intron

2017/04/25 15:00

プログラム実行時、最初にソースコード全体を解析されるということでしょうか?
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問