developer tip

C 표준은 진실 값을 0 또는 1로 명시 적으로 표시합니까?

optionbox 2020. 9. 24. 07:44
반응형

C 표준은 진실 값을 0 또는 1로 명시 적으로 표시합니까?


같지 않은 숫자 는 C 0로 간주되므로 다음과 같이 true작성할 수 있습니다.

int a = 16;

while (a--)
    printf("%d\n", a);  // prints numbers from 15 to 0

그러나, 나는 참 /의 거짓과 같이 정의되어 있는지 궁금했다 1/ 0나는 아래의 코드를 시도하므로, C에서 :

printf("True = %d, False = %d\n", (0 == 0), (0 != 0));  // prints: True = 1, False = 0

합니까 C 표준은 명시 적으로 진리의 참 값과 거짓으로 표시 1하고 0각각을?


C 표준이 명시 적으로 진리의 값을 표시 하는가 truefalse같은 01각각을?

는 C 표준을 정의 true하고 false같은 매크로에 stdbool.h되는 확장 10각각.

C11-§7.18 :

나머지 세 개의 매크로는 #if전처리 지시문 에 사용하기에 적합 합니다. 그들은

true

이는 정수 상수로 확장 1,

false

정수 상수로 확장되는 0[...]

운영자 ==!=

C11-§6.5.9 / 3 :

==(동일한)와 !=운영자가 자신의 낮은 우선 순위를 제외하고는 관계 연산자와 유사 (안 같음). 108) 각 연산자 1는 지정된 관계가 참이고 0거짓 이면 결과를 산출 합니다 . 결과 유형은 int입니다. 피연산자 쌍의 경우 관계 중 정확히 하나가 참입니다.


C11에는 명시 적으로 표시되어 있지 않습니다. 모든 언어 수준 작업 은 1을 true로 반환하고 NaN을 포함하여 0이 아닌 모든 것을 true로 허용합니다.

  • 에 대해 걱정하는 경우 _Bool표준에서 0과 1 만 유지하도록 요구하므로 true는 1이어야합니다 (§6.2.5 / 2).
  • 또한 <stdbool.h>매크로 true에서 1(§7.18 / 3)로 확장됩니다.
  • ==, !=, <, >, <=>=복귀 0 또는 1 (§6.5.8 / 6 §6.5.9 / 3).
  • !, &&||복귀 0 또는 1 (§6.5.3.3 / 5 / 3 §6.5.13, §6.5.14 / 3)
  • defined 0 또는 1로 확장 (§6.10.1 / 1)

그러나 모든 표준 라이브러리 함수는 예를 islower들어 진실을 위해 "0이 아님"이라고 말하면됩니다 (예 : §7.4.1 / 1, §7.17.5.1 / 3, §7.30.2.1 / 1, §7.30.2.2.1 / 4).


§6.2.5 / 2 : 유형 _Bool으로 선언 된 개체는 값 0과 1을 저장할 수있을만큼 큽니다.

§6.5.5.3 / 5 : 논리 부정 연산자의 결과 !는 피연산자의 값이 0과 같지 않으면 0, 피연산자의 값이 0과 같으면 1입니다.…

§6.5.8 / 6 : 각 연산자 <(보다 작음), >(보다 큼), <=(작거나 같음) 및 >=(보다 크거나 같음)은 지정된 관계가 참이면 1을, 그렇지 않으면 0을 산출합니다. 거짓입니다. 107)…

§6.5.9 / 3 : ==(같음) 및 !=(같지 않음) 연산자는 더 낮은 우선 순위를 제외하고 관계 연산자와 유사합니다 .108 ) 지정된 관계가 참이면 각 연산자는 1을, 맞으면 0을 산출합니다. 그릇된.

§6.5.13 / 3 : &&연산자는 두 피연산자가 모두 0과 같지 않으면 1을 산출합니다.

§6.5.14 / 3 : ||연산자는 피연산자 중 하나가 0과 같지 않으면 1을 산출합니다.

§6.10.1 / 1 :… 다음과 같은 경우 1로 평가되는 defined identifier— 또는 — defined ( identifier )형식의 단항 연산자 식을 포함 할 수 있습니다 .

§7.4.1 (문자 분류 기능) / 1 :이 하위 절의 기능은 다음과 같은 경우에만 0이 아닌 (참)을 반환합니다.

§7.18 / 3 : 나머지 3 개의 매크로는 #if전처리 지시문 에 사용하기에 적합 합니다. 그들은 — true— 정수 상수 1로 확장됩니다.…

§7.17.5.1 / 3 : atomic_is_lock_free일반 함수는 객체의 작업이 잠금이없는 경우에만 0이 아닌 (true)을 반환합니다.

§7.30.2.1 (와이드 문자 분류 기능) / 1 :이 하위 절의 기능은 다음과 같은 경우에만 0이 아닌 (참)을 반환합니다.

§7.30.2.2.1 / 4 : 다음 iswctype과 같은 경우에만 0이 아닌 값 (true)을 반환합니다.


C에서 부울 값 (특정 C bool/_Bool유형이 아닌 참 / 거짓 값을 의미 함)을 다룰 때 알아야 할 두 가지 표준 영역이 있습니다 .

첫 번째는 표현식 결과 와 관련이 있으며의 다양한 부분에서 찾을 수 있습니다 C11 6.5 Expressions(예 : 관계형 및 같음 연산자). 결론은 표현식에 의해 부울 값이 생성 될 때마다 ...

... 지정된 관계가 참이면 1을, 거짓이면 0을 산출합니다. 결과는 int 유형입니다.

So, yes, the result of any Boolean-generating expression will be one for true, or zero for false. This matches what you will find in stdbool.h where the standard macros true and false are defined the same way.

Keep in mind however that, following the robustness principle of "be conservative in what you send, liberal in what you accept", the interpretation of integers in the Boolean context is somewhat more relaxed.

Again, from various parts of 6.5, you'll see language like:

The || operator shall yield 1 if either of its operands compare unequal to 0; otherwise, it yields 0. The result has type int.

From that (and other parts), it's obvious that zero is considered false and any other value is true.


As an aside, the language specifying what value are used for Boolean generation and interpretation also appear back in C99 and C89 so they've been around for quite some time. Even K&R (ANSI-C second edition and the first edition) specified that, with text segments such as:

Relational expressions like i > j and logical expressions connected by && and || are defined to have value 1 if true, and 0 if false.

In the test part of if, while, for, etc, "true" just means "non-zero".

The && operator ... returns 1 if both its operands compare unequal to zero, 0 otherwise.

The || operator ... returns 1 if either its operands compare unequal to zero, and 0 otherwise.

The macros in stdbool.h appear back in C99 as well, but not in C89 or K&R since that header file did not exist at that point.


You are mixing up a lot of different things: control statements, operators and boolean types. Each have their own rules.

Control statements work like for example the if statement, C11 6.4.8.1:

In both forms, the first substatement is executed if the expression compares unequal to 0.

while, for etc have the same rule. This has nothing to do with "true" or "false".

As for operators that are supposedly yielding a boolean result, they are actually yielding an int with value 1 or 0. For example the equality operators, C11 6.5.9:

Each of the operators yields 1 if the specified relation is true and 0 if it is false

All of the above is because C did not have a boolean type until the year 1999, and even when it did get one, the above rules weren't changed. So unlike most other programming languages where statements and operators yield a boolean type (like C++ and Java), they just yield an int, with a value zero or not zero. For example, sizeof(1==1) will give 4 in C but 1 in C++.

The actual boolean type in C is named _Bool and requires a modern compiler. The header stdbool.h defines macros bool, true and false, that expand to _Bool, 1 and 0 respectively (for compatibility with C++).


It is however considered good programming practice to treat control statements and operators as if they actually required/yielded a boolean type. Certain coding standards like MISRA-C recommend such practice. That is:

if(ptr == NULL) instead of if(ptr).

if((data & mask) != 0) instead of if(data & mask).

The aim of such style is to increase type safety with the aid of static analysis tools, which in turn reduces bugs. Arguably, this style is only meaningful if you do use static analysers. Though in some cases it leads to more readable, self-documenting code, for example

if(c == '\0') 

Good, the intent is clear, the code is self-documenting.

versus

if(c) 

Bad. Could mean anything, and we have to go look for the type of c to understand the code. Is it an integer, a pointer or a character?


I've programmed in many languages. I've seen true be 1 or -1 depending on the language. The logic behind true being 1 was that a bit was either a 0 or 1. The logic behind true being -1 was that the ! operator was a one's complement. It changed all the 1's to 0's and all the 0's to 1's in an int. So, for an int, !0 = -1 and !(-1) = 0. This has tripped me up enough that I don't compare something to be == true, but instead compare it to be != false. That way, my programming style works in every language. So my answer is to not worry about it, but program so that your code works correctly either way.


This answer needs to be looked at a bit more closely.

The actual definition in C++ is that anything not 0 is treated as true. Why is this relevant? Because C++ doesn't know what an integer is by how we think about it--we create that meaning, all it holds is the shell and rules for what that means. It knows what bits are though, that which make up an integer.

1 as an integer is loosely represented in bits, say an 8-bit signed int as 0000 0001. Many times what we see visually is a bit of a lie, -1 is a much more common way to represent it because of the signed nature of 'integer'. 1 really can't mean true proper, why? Because it's NOT operation is 1111 1110. That's a really major issue for a boolean. When we talk about a boolean, it's just 1 bit--it's really simple, 0 is false and 1 is true. All the logic operations hold as trivial. This is why '-1' should be designated as 'true' for integers (signed). 1111 1111 NOT'ed becomes 0000 0000---the logic holds and we're good. Unsigned ints is a little bit tricky and were a lot more commonly used in the past--where 1 means true because it's easy to imply the logic that 'anything not 0 is true'.

That's the explanation. I say the accepted answer here is wrong--there is no clear definition in the C/C++ definition. A boolean is a boolean, you can treat an integer as a boolean, but the fact the output is an integer says nothing about the operation actually being done is bitwise.


It happened because of the Relational Operators in your printf statement.

Operator == and operator !=

Since (0 == 0) holds true so, it gives a value 1

whereas, (0 != 0) doesn't hold true so, gives a value 0 .

참고URL : https://stackoverflow.com/questions/37291681/does-the-c-standard-explicitly-indicate-truth-value-as-0-or-1

반응형