간단한 질문은 정말로; 이 값들 사이에 차이가 있습니까 (그리고 BOOL과 bool 사이에 차이가 있습니까)? 동료는 Objective-C에서 다른 것으로 평가한다고 언급했지만 각각의 .h 파일에서 typedef를 볼 때 YES / TRUE / true는 모두 정의 1
되었고 NO / FALSE / false는 모두로 정의되었습니다 0
. 실제로 어떤 차이가 있습니까?
간단한 질문은 정말로; 이 값들 사이에 차이가 있습니까 (그리고 BOOL과 bool 사이에 차이가 있습니까)? 동료는 Objective-C에서 다른 것으로 평가한다고 언급했지만 각각의 .h 파일에서 typedef를 볼 때 YES / TRUE / true는 모두 정의 1
되었고 NO / FALSE / false는 모두로 정의되었습니다 0
. 실제로 어떤 차이가 있습니까?
답변:
실질적인 차이가 없습니다 제공 당신이 사용하는 BOOL
논리 값으로 변수. C는 0으로 평가되는지 여부에 따라 부울 표현식을 처리합니다. 따라서 :
if(someVar ) { ... }
if(!someVar) { ... }
와 같은 의미
if(someVar!=0) { ... }
if(someVar==0) { ... }
그렇기 때문에 모든 기본 유형 또는 표현식을 부울 테스트 (예 : 포인터 포함)로 평가할 수 있습니다. 후자는 아니라 전자를해야합니다.
참고가 있다는 것입니다 당신이 소위에 둔각 값을 할당하면 차이 BOOL
때문에 항상 논리 값으로 사용할하고 그들의에서 그들을 지정, 특정 값에 대한 변수 테스트 #define
값.
중요한 것은 문자 비교를 사용하여 부울을 테스트하지 마십시오. 예가 someVar
아닌 0이 아닌 값을 할당 할 수 있기 때문에 위험 할뿐만 아니라 더 중요한 것은 의도를 올바르게 표현하지 못하는 것입니다.
if(someVar==YES) { ... } // don't do this!
if(someVar==NO ) { ... } // don't do this either!
다시 말해, 사용하도록 의도되고 문서화 된 구성을 사용하면 C의 상처를 입은 세상에서 벗어날 수 있습니다.
와 사이에 차이 가 있다고 생각 하는 이유는 다음 웹 페이지에서 확인하십시오. http://iosdevelopertips.com/objective-c/of-bool-and-yes.htmlbool
BOOL
프리미티브 유형 BOOL
이 아니기 때문에 unsigned char
유형의 변수는 및 BOOL
이외의 값을 포함 할 수 있습니다 .YES
NO
이 코드를 고려하십시오.
BOOL b = 42;
if (b) {
printf("b is not NO!\n");
}
if (b != YES) {
printf("b is not YES!\n");
}
출력은 다음과 같습니다.
b는 아니요가 아닙니다!
b는 그렇습니다!
대부분의 사람들에게 이것은 불필요한 관심사이지만 실제로 부울을 원한다면을 사용하는 것이 좋습니다 bool
. 추가해야합니다 : iOS SDK는 일반적으로 BOOL
인터페이스 정의에서 사용하므로 BOOL
.
bool
때문에 int
또는 char
차이를 숨기려면 때로는 #define과 함께 또는 부울로 사용하는 것이 전통 이었습니다. 사실, 현재 표준조차도 bool
내부 구조를 검사하지 못하는 방식으로 구현 해야하는지 확실하지 않습니다 .
printf
거짓말은 거짓말입니다. 의 값은 b
아닙니다 YES
그것은 어떤 조건 시험 인 "제로가 아닌"입니다. 따라서 printf("b is not zero")
반드시와 같을 필요는 없습니다 YES
. 이 경우 b
"0이 아님"및 " 예가 아님"입니다.
나는 이것에 대해 철저한 테스트를 수행했습니다. 내 결과는 스스로 말해야합니다.
//These will all print "1"
NSLog(@"%d", true == true);
NSLog(@"%d", TRUE == true);
NSLog(@"%d", YES == true);
NSLog(@"%d", true == TRUE);
NSLog(@"%d", TRUE == TRUE);
NSLog(@"%d", YES == TRUE);
NSLog(@"%d", true == YES);
NSLog(@"%d", TRUE == YES);
NSLog(@"%d", YES == YES);
NSLog(@"%d", false == false);
NSLog(@"%d", FALSE == false);
NSLog(@"%d", NO == false);
NSLog(@"%d", false == FALSE);
NSLog(@"%d", FALSE == FALSE);
NSLog(@"%d", NO == FALSE);
NSLog(@"%d", false == NO);
NSLog(@"%d", FALSE == NO);
NSLog(@"%d", NO == NO);
//These will all print "0"
NSLog(@"%d", false == true);
NSLog(@"%d", FALSE == true);
NSLog(@"%d", NO == true);
NSLog(@"%d", false == TRUE);
NSLog(@"%d", FALSE == TRUE);
NSLog(@"%d", NO == TRUE);
NSLog(@"%d", false == YES);
NSLog(@"%d", FALSE == YES);
NSLog(@"%d", NO == YES);
NSLog(@"%d", true == false);
NSLog(@"%d", TRUE == false);
NSLog(@"%d", YES == false);
NSLog(@"%d", true == FALSE);
NSLog(@"%d", TRUE == FALSE);
NSLog(@"%d", YES == FALSE);
NSLog(@"%d", true == NO);
NSLog(@"%d", TRUE == NO);
NSLog(@"%d", YES == NO);
출력은 다음과 같습니다.
2013-02-19 20:30:37.061 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.061 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.072 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.073 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.073 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.074 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.074 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.075 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.075 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.076 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.077 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.077 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.078 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.078 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.079 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.079 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.080 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.080 BooleanTests[27433:a0f] 1
2013-02-19 20:30:37.081 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.081 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.082 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.091 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.092 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.093 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.093 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.094 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.094 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.095 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.095 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.096 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.096 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.097 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.098 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.101 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.102 BooleanTests[27433:a0f] 0
2013-02-19 20:30:37.102 BooleanTests[27433:a0f] 0
if
또는 에서 부울이 아닌 값을 취하는 언어에 익숙하지 않았습니다 while
. 처럼 ... while("guitar gently weeps")
작동하지 않아야합니다 ...
if (user_id = ROOT_UID)
주 (위험!) 차이가 사이 true
및 YES
JSON 직렬화에 있습니다.
예를 들어 JSON 유형의 서버 요청이 있으며 json sence로 true / false를 보내야합니다.
NSDictionary *r1 = @{@"bool" : @(true)};
NSDictionary *r2 = @{@"bool" : @(YES)};
NSDictionary *r3 = @{@"bool" : @((BOOL)true)};
그런 다음 다음을 보내기 전에 JSON 문자열로 변환합니다.
NSData *data = [NSJSONSerialization dataWithJSONObject:requestParams options:0 error:nil];
NSString *jsonString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
결과는
jsonString1 // {"bool":1}
jsonString2 // {"bool":true}
jsonString3 // {"bool":true}
API 로직으로 인해 jsonString1
오류가 발생할 수 있습니다.
따라서 Objective-C의 부울에주의하십시오.
요약하면, 유형 이 정확 @YES
하고 캐스팅 된 값만 JSON 직렬화 로 변환됩니다 . (even ) 과 같은 다른 표현식 은 유형이 있으며 JSON으로 변환됩니다 .@((BOOL)expression)
__NSCFBoolean
true
@(expression1 && expression2)
@(YES && YES)
__NSCFNumber (int)
1
추신 당신은 단순히 문자열 값 부울을 사용할 수 있습니다
@{@"bool" : @"true"}; // in JSON {"bool":true}
아무도 언급하지 않은 미묘한 버그가 있습니다.
int i = 2;
if(i); //true
if(i==YES); // false
if((!!i)==YES); //true
여기서 문제는 그저 문제 (YES==1)
이며 C에서는 비교가 부울이 아니라 값을 기반으로하는 비교입니다.
왜냐하면 (언어에 본질적인 것이 아니라 YES
) 단지 #define
가치 1
이기 때문에 가장 의미가 있어야합니다.
나는 그들이 더 많은 설명을 위해 YES / NO를 추가한다고 생각합니다. 예를 들면 다음과 같습니다.
[button setHidden:YES];
보다 나은 소리
[button setHidden:TRUE];
먼저 참과 거짓이 무엇인지 그리고 무엇을 의미하는지 먼저 살펴 보자.
람다 미적분학에서 if a else b else c라는 구조를 다음과 같이 구성 할 수 있습니다.
(\ifThenElse. <use if then else>)(\a. \b. \c. a b c)
JavaScript에서는 다음과 같습니다.
(function(ifThenElse) {
// use ifThenElse
})(function(a) {
return function(b) {
return function(c) {
return a(b)(c);
};
};
});
ifThenElse가 유용하기 위해서는 오른쪽 또는 왼쪽을 선택하는 기능 "true"가 필요하며 다른 옵션을 무시하면서 기능을 수행하거나 "true"옵션을 선택하는 "false"기능을 사용하지 않습니다.
이러한 기능을 다음과 같이 정의 할 수 있습니다.
(\true. <use true>)(\a. \b. a) and (\false. <use false>)(\a. \b. b)
JavaScript에서는 다음과 같습니다.
(function(True) {
// use True
})(function(a) {
return function(b) {
return a;
}
});
(function(False) {
// use True
})(function(a) {
return function(b) {
return b;
}
});
이제 우리는 다음을 할 수 있습니다
(\true. \false. \ifThenElse. \doThis. \doThat. ifThenElse true doThis doThat)
(\a. \b. a)(\a. \b. b)(\a. \b. \c. a b c)(\a. ())(\a. ())
람다 미적분은 인쇄 / 수학 / 문자열과 같은 서비스를 제공하지 않기 때문에 doThis와 doThat (\ a. ())으로 할 수 있습니다. 우리가 할 수있는 일은 아무것도하지 않고 수행 한 것입니다. 원하는 부작용을 제공하는 시스템)
이것을 실제로 보도록합시다.
(function(True) {
return (function(False) {
return (function(ifThenElse) {
return (function(doThis) {
return (function(doThat) {
return ifThenElse(True)(doThis)(doThat);
});
});
});
})
})(function(a) {
return function(b) {
return a;
}
})(function(a) {
return function(b) {
return b;
}
})(function(a) {
return function(b) {
return function(c) {
return a(b)(c);
};
};
})(function(a) { console.log("you chose LEFT!"); })
(function(a) {console.log("you chose RIGHT");})();
배열 / 맵 / 인수 / 또는 둘 이상의 명령문을 사용하여 여러 함수로 나눌 수 있다면 단순화 될 수있는 깊은 환경이지만, 정확히 하나의 인수의 함수로 자신을 제한 할 수있는 한 순수하게 유지하고 싶습니다. 뿐.
True / False라는 이름에는 고유 한 의미가 없으므로 예 / 아니오, 왼쪽 / 오른쪽, 오른쪽 / 왼쪽, 0 / 하나, 사과 / 오렌지로 쉽게 이름을 바꿀 수 있습니다. 어떤 선택을하든 선택 자의 선택에 의해서만 발생한다는 점에서 의미가 있습니다. 따라서 "LEFT"가 인쇄되면 선택자가 사실 일 수 있다는 것을 알고 있으며이 지식을 바탕으로 추가 결정을 안내 할 수 있습니다.
요약하자면
function ChooseRight(left) {
return function _ChooseRight_inner(right) {
return right;
}
}
function ChooseLeft(left) {
return function _ChooseLeft_inner(right) {
return left;
}
}
var env = {
'0': ChooseLeft,
'1': ChooseRight,
'false': ChooseRight,
'true': ChooseLeft,
'no': ChooseRight
'yes': ChooseLeft,
'snd': ChooseRight,
'fst': ChooseLeft
};
var _0 = env['0'];
var _1 = env['1'];
var _true = env['true'];
var _false = env['false'];
var yes = env['yes'];
var no = env['no'];
// encodes church zero or one to boolean
function lambda_encodeBoolean(self) {
return self(false)(true);
}
// decodes a Boolean to church zero or one
function lambda_decodeBoolean(self) {
console.log(self, self ? env['true'] : env['false']);
return self ? env['true'] : env['false'];
}
lambda_decodeBoolean('one' === 'two')(function() {
console.log('one is two');
})(function() {
console.log('one is not two');
})();
lambda_decodeBoolean('one' === 'one')(function() {
console.log('one is one');
})(function() {
console.log('one is not one');
})();