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

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

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

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

Q&A

解決済

3回答

34620閲覧

C言語のtrueとfalseについて

strike1217

総合スコア651

C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

2グッド

1クリップ

投稿2016/09/21 02:58

.#define true 1
.#define false 0

というふうに定義されていると思います。

しかし
int main()
return 0;

とあった場合、return 0; → return false;とも書けますよね?
return 0;は”成功している”という意味で返しますよね??
return false;だと失敗してる と読み取れるのですが・・・

なぜこのようなわかりにくい記述をするのでしょうか?

それから、while(i)とあった場合に (i != 0) という意味と同じだと思います。
while(i == 0)この場合は (i == 0 != 0) という意味にはなりませんよね??

条件式を入れると !=0 にはならなくて、
条件式を入れないと、自動的に !=0になる

という解釈であっていますか?

教えてください。

DrqYuto, Kchan_01👍を押しています

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

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

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

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

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

guest

回答3

0

ベストアンサー

こんにちは。

なぜこのようなわかりにくい記述をするのでしょうか?

0をfalseと解釈するかどうかは文脈により変わらざる得ません。

例えばWindows APIの戻り値の0は概ね成功を示します。一般に成功は1つですが、失敗は様々な原因があるのでエラー・コードを複数割り当てたいという要求から来る仕様と思います。(もちろん例外はあります。)
strcmp()やmemcmp()も似た理由で一致した時0を返却しますね。
同様にmain()関数の戻り値はOSへ返却されます。成功は1つでエラーを複数返却できるようにしたいということです。

では、なぜC言語は0をfalse、非0をtrueと解釈するのか?が問題と思います。上記を是とするなら、0をtrue、1をfalseに割り当てた方が分かりやすいと言う話に帰着できますね。
すると、true || false → tureですから0 || 1 → 0でないといけませんね。
しかし、0 | 1 → 1です。これではバグ地獄にハマると思います。

従って、0をfalseと定義するかどうかは文脈により、変わらざる得ないと思います。

条件式を入れると !=0 にはならなくて、
条件式を入れないと、自動的に !=0になる
という解釈であっていますか?

違います。どちらの場合も!=0で判定しています。
C言語は元々bool型は存在しませんでした。ifやwhile等の中には整数型を記述し、それが0か0でないかを判定します。現在は_Bool型が存在しますが状況はあまり変わっていないです。
また、第5回 型と型変換で言及されてますが、C言語の関係演算子の結果はint型です。
つまり、条件式もそれ以外でも結果はint型ですから、if文やwhile文はそれが0か非0かで分岐しているということになります。

なお、C++では最初からbool型が定義されているので状況は異なります。

投稿2016/09/21 03:58

Chironian

総合スコア23272

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

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

strike1217

2016/09/21 04:13

ほぉぉぉ・・・ わかりやすいです。 ありがとうございます。
strike1217

2016/09/21 04:17

なぜ true || false → true になるのですか? "||"の記号と "|" の記号は全く関係のない別物ですよね?
Chironian

2016/09/21 07:11

> なぜ true || false → true になるのですか? 「真 または 偽」は真と定義されているからです。 http://www004.upp.so-net.ne.jp/s_honma/logic/logic.htm これは定義なのでそれに理由は必要ありません。強いて言えば、そのような定義を使って役に立つ結果を導いた人達がたくさんいるから、この定義を使う人が多数いるのです。 C言語も多数の人が使っている定義を採用したと理解してます。 > "||"の記号と "|" の記号は全く関係のない別物ですよね? どちらも同じ真理値表を用いて定義されており、密接な関係があります。 たまたま一致しているわけではないですよ。 return true;で0を返却するためにはtrue=0とするしかなく、その場合||の定義が|と異なってしまい、上記の密接な関係が崩れてしまいます。そのようなコンパイラを作ることも当然可能ですが、バグ地獄を見ると思います。 それよりはreturn false;でも正常終了を返却できることが許容されてます。 そもそも書けるから書いていいわけではない記述は他にもいくらでもあります。 return false;で正常終了を返却できることは、その1つに過ぎません。 正常終了を返却したい時にreturn false;と書くのは愚か者です。例えば#define SUCCESS 0としてreturn SUCCESS;すれば良いだけです。
strike1217

2016/09/21 10:38

ふむふむ・・・ 流石ですね。 ありがとうございます。
strike1217

2016/09/21 11:07

すいません。 もう一点、お願いします。 if文やwhile文の条件式の中で (i == 0 || i == 5) と (i == 0 | i == 5) は同じ結果になると思いますが、Cを作った人はなぜ "||"と"|" を作ったのですかね? 逆に、"||"この演算子しか使えない場面というものはあるのですか?
Chironian

2016/09/21 12:10

"||"は2値のOR演算です。"|"はビット毎のOR演算です。 例えば、int x, y, z0, z1;の時、z0 = x || y;とz1 = x | y;では結果が異なります。 x=1; y=2;の時、z0は1、z1は3になる筈です。 最終的に0か非0かで判定する場合ORだけでは結果が同じに見えますが、ANDが交じると大化けします。 z2 = (x || y) && 4; z3= (x | y) & 4;を計算するとz2は1、z3は0になります。 "||"この演算子しか使えない場面はないと思いますが、"||"を使った方が楽な場面はあります。上記のz2の結果がほしい時"||"がなかったらちょっと面倒かと。("||"がないなら"&&"もないでしょうから、更に面倒ですね。)
strike1217

2016/09/21 23:58

ありがとうございます。
guest

0

(質問に対してはChironianさん回答でカバーされていると思いますが、気になった点だけコメントします。)

とあった場合、return 0; → return false;とも書けますよね?

そのように書くべきではありません。プログラムのコードをある方法で"書ける"ことと、そう書くことが"望ましい"かという観点は区別すべきです。

「main関数からの値0返却はプログラムの正常終了を表す」、「C言語での偽値(false)は値0である」はいずれも事実です。両者よりreturn false;はコンピュータ(C言語コンパイラ)にとってはreturn 0;と同義ですし、確かに動作上の問題は生じません。

しかしソースコード上にreturn false;と書いた場合、それは「main関数から偽値(false)を返す」という意味(Semantics; セマンティクス)の、プログラマからの表明になります。これ自体は何の意味も持ちませんから、そのように書くべきではないという回答になります。

投稿2016/09/21 08:27

yohhoy

総合スコア6191

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

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

strike1217

2016/09/21 10:39

わかりました。 ありがとうございます。
guest

0

return 0;は”成功している”という意味で返しますよね??

return false;だと失敗してる と読み取れるのですが・・・

mainの戻り値は慣習的に異常があるかを返します。
「異常ががあるか?」なら正常終了はfalseを返すのが自然ですね。

また、単純に異常のある無しではなく、エラーコードを返すこともあります。
このときはtrue/falseではなく本当に数値を返したいです。


条件式を入れると !=0 にはならなくて、

条件式を入れないと、自動的に !=0になる

例えば
(i == 0)はiが0なら1(環境によるのかもしれないがとにかく0以外)、
そうでないなら0を返します。
で、while文は条件部分が0以外なら実行します。それだけです。

投稿2016/09/21 03:25

ozwk

総合スコア13528

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

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

strike1217

2016/09/21 04:14

ありがとうございます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.47%

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

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

質問する

関連した質問