C #에 조건부 XOR
연산자 가없는 이유는 무엇입니까?
예:
true xor false = true
true xor true = false
false xor false = false
C #에 조건부 XOR
연산자 가없는 이유는 무엇입니까?
예:
true xor false = true
true xor true = false
false xor false = false
& | ^
)와 조건 연산자 ( && ||
)를 언급하고 있다고 생각 합니다. 하지만 당신 말이 맞습니다. (물론) 논리적 XOR이 있습니다 ...
답변:
C #에서 조건부 연산자는 필요한 경우 에만 보조 피연산자를 실행 합니다 .
XOR 은 정의에 따라 두 값을 모두 테스트 해야 하므로 조건부 버전은 어리석은 것입니다.
예 :
논리적 AND : &
-매번 양쪽을 테스트합니다.
논리적 OR : |
-매번 양쪽을 테스트합니다.
조건부 AND : &&
-첫 번째면이 참인 경우 두 번째 면만 테스트합니다.
조건부 OR : ||
-첫 번째면이 거짓이면 두 번째 면만 테스트합니다.
질문이 조금 구식이지만 ...
이 연산자가 작동하는 방식은 다음과 같습니다.
true xor false = true
true xor true = false
false xor true = true
false xor false = false
다음은! = 연산자가 bool 유형에서 작동하는 방식입니다.
(true != false) // true
(true != true) // false
(false != true) // true
(false != false) // false
보시다시피 ^^
존재하지 않는 것은 기존의!=
!=
이것을 위해 일할 것이라는 것을 깨닫지 못했다 .
AND
하고 OR
있지만, 같은 아무것도 XOR
. 또는 적어도 우리는 몰랐어요 !=
:) @TheEvilGreebo
^
는 부울 피연산자와 함께 사용할 때 부울 연산자 라고 명시 적으로 명시 합니다. "부울 피연산자의 경우 ^ 연산자는 부등식 연산자! ="와 동일한 결과를 계산합니다. 를 사용하여 비트 xor 정수 피연산자를 사용할 수도 있습니다 ^
. C #은 C가 아닙니다.
설명처럼 ^ 연산자는 정수 유형과 부울 모두에서 작동합니다.
참조 MSDN의 ^ 연산자 (C # 참조) :
이진 ^ 연산자는 정수 유형 및 부울에 대해 사전 정의됩니다. 정수 유형의 경우 ^는 피연산자의 비트 배타적 OR을 계산합니다. bool 피연산자의 경우 ^는 피연산자의 논리적 배타적 또는 논리 연산을 계산합니다. 즉, 피연산자 중 정확히 하나가 참인 경우에만 결과가 참입니다.
이 질문이 제기 된 2011 년 이후로 문서가 변경되었을 수 있습니다.
^
이것을 언급 하고 5 년 앞선 다른 답변에 대한 의견이나 편집으로 더 적절 해 보입니다 . 나는 아무것도 바뀌지 않았다고 의심한다.
네, 그렇습니다.
bool b1 = true;
bool b2 = false;
bool XOR = b1 ^ b2;
i1
바이트와 마찬가지로). 이것은 100 % 정의되고 안전하게 관리되는 행동입니다. CLR은 대략적인 것이 아닙니다.; 이 동작을 처음 본 것은 Microsoft Pex를 사용할 때였습니다.
조건부 xor는 존재하지 않지만 xor가 부울에 대해 정의되고 모든 조건부 비교가 부울로 평가되므로 논리 xor를 사용할 수 있습니다.
따라서 다음과 같이 말할 수 있습니다.
if ( (a == b) ^ (c == d))
{
}
1
. 이것은 약간 알려진 사실입니다. 두 개의 거짓이 아닌 부울의 xor가 여전히 거짓이 아닌 상황에서 끝날 수 있습니다! 즉,이 특정 코드에서 xor 연산자는 [0,1]의 값에만 적용되므로 내 의견이 (완전히) 적용되지 않습니다.
&
또한 취약합니다.
&&
것처럼 컴파일했기 때문 &
입니다.
논리 xor 연산자 가있는 동안^
더 없다 조건부 xor 연산자 . 다음을 사용하여 두 값 A와 B의 조건부 xor를 얻을 수 있습니다.
A ? (!B) : B
괄호는 필요하지 않지만 명확성을 위해 추가했습니다.
The Evil Greebo가 지적한 것처럼 이것은 두 표현을 모두 평가하지만 xor는 and and or 처럼 단락 될 수 없습니다 .
0101 ^ 0011
has the value 0110
.
조건부 (단락) XOR과 같은 것은 없습니다. 조건부 연산자는 첫 번째 인수 만보고 최종 결과를 확실히 알 수있는 방법이있을 때만 의미가 있습니다. XOR (및 덧셈)에는 항상 두 개의 인수가 필요하므로 첫 번째 인수 후에 단락 할 방법이 없습니다.
A = true를 안다면 (A XOR B) =! B입니다.
A = false를 안다면 (A XOR B) = B입니다.
두 경우 모두 A는 알지만 B는 알지 못한다면 충분히 알지 못합니다 (A XOR B). 답을 계산하려면 항상 A와 B의 값을 모두 배워야합니다. 두 값없이 XOR을 해결할 수있는 사용 사례는 말 그대로 없습니다.
XOR은 정의에 따라 네 가지 경우가 있습니다.
false xor true = true
true xor false = true
true xor true = false
false xor false = false
다시 말하지만, 위의 내용에서 첫 번째 값을 아는 것만으로는 두 번째 값을 알지 않고는 답을 얻을 수 없다는 것이 분명합니다. 그러나 귀하의 질문에서 첫 번째 경우를 생략했습니다. 대신 원한다면
false op true = false (or DontCare)
true op false = true
true op true = false
false op false = false
그런 다음 단락 조건부 작업을 통해 실제로 얻을 수 있습니다.
A && !B
그러나 그것은 XOR이 아닙니다.
이 질문은 정서적으로 답변되었지만 다른 상황에 직면했습니다. 조건부 XOR이 필요 없다는 것은 사실입니다. ^ 연산자를 사용할 수 있다는 것도 사실입니다. 그러나 피연산자의 "true || false"상태 만 테스트해야하는 경우 ^가 문제를 일으킬 수 있습니다. 예를 들면 :
void Turn(int left, int right)
{
if (left ^ right)
{
//success... turn the car left or right...
}
else
{
//error... no turn or both left AND right are set...
}
}
이 예에서 left가 10 (0xa)으로 설정되고 right가 5 (0x5)로 설정되면 "success"분기가 입력됩니다. 이 (어리 석다면 단순한) 예제의 경우, 동시에 좌회전과 우회전을해서는 안되므로 버그가 발생합니다. 질문자로부터 얻은 것은 그가 실제로 조건부를 원했다는 것이 아니라 xor에 전달 된 값에 대해 참 / 거짓을 수행하는 간단한 방법입니다.
매크로는 트릭을 수행 할 수 있습니다.
#define my_xor(a, b) ( ((a)?1:0) ^ ((b)?1:0) )
내가 틀렸다면 자유롭게 때려 눕히십시오 : o)
나는 이것을 게시 한 후 아래 jimreed의 답변을 읽었으며 (나쁜 Yapdog!) 실제로 더 간단합니다. 그것은 효과가있을 것이고 나는 그의 대답이 왜 거절되었는지 전혀 모른다 ...
if
부울 표현식이 필요하며 int로 컴파일되지도 않습니다.
!=
대체로 어떻게 작동합니까?