क्या करता है (x ^ 0x1)! = 0 मतलब?


183

मैं निम्नलिखित कोड स्निपेट पर आया था

if( 0 != ( x ^ 0x1 ) )
     encode( x, m );

क्या x ^ 0x1मतलब है? क्या यह कुछ मानक तकनीक है?


97
कोड ऑबफ्यूजन काफी मानक है।
वर्षा 7

47
इसे "सामान्य" समीकरण के समान दृष्टिकोण से हल किया जा सकता है: 0 != (x ^ 1)→ xor दोनों तरफ 1 → (0 ^ 1) != (x ^ 1 ^ 1)→ सरलीकृत →1 != x
स्कोर_उंडर

4
मैं नहीं देखता कि if (1 != x)लिखना कितना कठिन है।
एड्रियानो वरोली पियाजे

12
विभिन्न टिप्पणियाँ, पहले @Spook द्वारा, स्पष्ट रूप से इंगित किया जाता है कि इसमें typeसे xकुछ नहीं दिया गया है - इसलिए हम नहीं जानते कि यह इस C ++ टैग की गई समस्या में पूर्णांक है। निश्चित रूप से, अगर यह C या xपूर्णांक है, तो उत्तर आसान है, लेकिन यह एक दिया नहीं है और ओवरलोडिंग की संभावना operator ^मौजूद है।
chux -

11
मैं नहीं देखता कि यह कैसे इतने सारे
उठाव करता है

जवाबों:


277

XOR ऑपरेशन ( x ^ 0x1) बिट को निष्क्रिय करता है। इसलिए अभिव्यक्ति का प्रभावी रूप से मतलब है: यदि x का 0 बिट 0 है, या x का कोई अन्य बिट 1 है, तो अभिव्यक्ति सही है।

इसके विपरीत एक्स == 1 होने पर अभिव्यक्ति झूठी है।

तो परीक्षण के रूप में ही है:

if (x != 1)

और इसीलिए (यकीनन) अनावश्यक रूप से अशिक्षित है।


39
अरे, आप संदर्भ नहीं जानते। यदि x किसी प्रकार का बिट फ्लैग है, तो यह IMO वास्तव में इसे लिखने के लिए अधिक स्पष्ट है क्योंकि यह अब =! ऑपरेटर का उपयोग करने से है।
भूत

40
@Spook: यह सिर्फ एक बिट ध्वज का परीक्षण नहीं कर रहा है - यह x की संपूर्ण चौड़ाई का परीक्षण कर रहा है। यदि आप सिर्फ एक बिट का परीक्षण करना चाहते हैं, तो स्पष्ट मुहावरे हैं, जैसे कि बिटवाइज़ का उपयोग करना और।
पॉल आर

115
अनावश्यक रूप से बाधित? क्या आप नहीं जानते कि कोड को बाधित करना हमारा काम है। अगर हमने सरल कोड लिखा है जो किसी को भी समझ में आ सकता है, क्यों, दुनिया में हमारे पदों की धार्मिक पवित्रता कहाँ जाएगी? हम अचानक हर किसी की तरह आम कार्यकर्ता होंगे। अंतर्विरोध स्वाभाविक रूप से आवश्यक है।
थॉम

31
वास्तव में स्पूक सही है। परीक्षण (x! = 1) समकक्ष नहीं है। कोड C ++ हो सकता है (और C ++ में, ^ एक ऑपरेटर हो सकता है जो कुछ भी करता है)। तो आप संदर्भ नहीं जानते, @Spook सही है।
xryl669

82
@TheThom уєт уσυ Tяιтι ιи ℓє яαя тobт
bobobobo

78
  • ^बिटवार XOR ऑपरेशन है
  • 0x1है 1हेक्स अंकन में
  • x ^ 0x1अंतिम बिट को उल्टा कर देंगे x(ऊपर दिए गए लिंक में XOR सत्य तालिका का संदर्भ लें यदि यह आपके लिए स्पष्ट नहीं है)।

तो, स्थिति (0 != ( x ^ 0x1 ))सही होगी यदि x1 से अधिक है या यदि अंतिम बिट xहै 0. जो केवल x == 1 को एक ऐसे मूल्य के रूप में छोड़ता है जिस पर स्थिति झूठी होगी। तो यह बराबर है

if (x != 1)

इस तरह के एक साधारण स्थिति को लागू करने के लिए पीएस हेल, मैं जोड़ सकता हूं। ऐसा मत करो। और यदि आपको जटिल कोड लिखना होगा, तो एक टिप्पणी छोड़ दें । मैं तुमसे विनती करता हूँ।


7
यह नहीं है x==0; 4 ^ 0x1सच है, लेकिन 4==0स्पष्ट रूप से गलत है।
फ्रेड फू

4
"स्थिति बराबर लगती है if (x == 0)", क्या यह बराबर नहीं है x != 1?
एंड्रयू-डुफ्रेसने

6
समतुल्यता पूर्व निर्धारित xप्रकार है। यदि यह एक है floatया doubleहै, तो मेरा मानना है कि अभिव्यक्ति के लिए सच प्राप्त होते हैं 1.0 <= x < 2.0। और यदि xकोई उपयोगकर्ता-परिभाषित प्रकार है, तो अभिव्यक्ति सही हो सकती है यदि xएक यूगो, कंगारू, प्रसिद्ध संगीतकार का जन्मदिन है, या कोई भी संख्या जो चीन में मौजूदा डॉलर-मूल्य वाली चाय के मूल्य के साथ कम से कम तीन अंक साझा करती है।
सुपरकैट

4
@supercat कोई / के operator^लिए नहीं है । floatdouble
शराबी

1
@ सुपरफ़ैट: ​​जब फ़्लोटिंग-पॉइंट से पूर्णांक में रूपांतरण के लिए कहा जाता है, तो रूपांतरण निहित होता है (इसमें कास्ट सिंटैक्स की आवश्यकता नहीं होती है)। लेकिन बिटकॉइन ऑपरेटरों द्वारा कोई रूपांतरण शुरू नहीं किया जाता है, वे केवल फ्लोटिंग-पॉइंट प्रकारों के लिए विफल होते हैं।
बेन Voigt

49

यह ओवरसाइम्प्लीफाइड स्पष्टीकरण के रूप में लग सकता है, लेकिन अगर कोई इसके माध्यम से जाना चाहेगा तो यह धीरे-धीरे नीचे है:

^c, c ++ और c # में एक बिटवाइज़ XOR ऑपरेटर है।

बिटवाइज़ XOR, समान लंबाई के दो बिट पैटर्न लेता है और संगत बिट्स के प्रत्येक जोड़े पर तार्किक अनन्य OR ऑपरेशन करता है।

एक्सक्लूसिव OR एक लॉजिकल ऑपरेशन है जो दोनों आउटपुट अलग-अलग होने पर सच होता है (एक सच है, दूसरा गलत है)।

सच्चाई तालिका की एक XOR ख :

a           b        a xor b
----------------------------
1           1           0
1           0           1
0           1           1
0           0           0

तो आइए 0 == ( x ^ 0x1 )बाइनरी स्तर पर अभिव्यक्ति का वर्णन करें :

             what? xxxxxxxx (8 bits)
               xor 00000001 (hex 0x1 or 0x01, decimal 1)    
             gives 00000000
---------------------------
the only answer is 00000001

इसलिए:

   0 == ( x ^ 0x1 )    =>    x == 1
   0 != ( x ^ 0x1 )    =>    x != 1

34

यह एक्सक्लूसिव OR (XOR) ऑपरेटर है। यह समझने के लिए कि यह कैसे काम करता है आप इस सरल कोड को चला सकते हैं

    std::cout << "0x0 ^ 0x0 = " << ( 0x0 ^ 0x0 ) << std::endl;
    std::cout << "0x0 ^ 0x1 = " << ( 0x0 ^ 0x1 ) << std::endl;
    std::cout << "0x1 ^ 0x0 = " << ( 0x1 ^ 0x0 ) << std::endl;
    std::cout << "0x1 ^ 0x1 = " << ( 0x1 ^ 0x1 ) << std::endl;

आउटपुट होगा

0x0 ^ 0x0 = 0
0x0 ^ 0x1 = 1
0x1 ^ 0x0 = 1
0x1 ^ 0x1 = 0

तो यह अभिव्यक्ति

0 != ( x ^ 0x1 )

केवल x =! 0x1 होने पर समान सत्य होगा।

यह स्वयं एक्स नहीं बदलता है। यह केवल जाँच करता है कि क्या x 0 के बराबर है या 1. इस rxpression को बदला जा सकता है

if ( x != 0x1 )

19

यह जांच करता है कि xवास्तव में है नहीं 0x1... xoring xसाथ 0x10 में परिणाम होगा ही अगर xहै 0x1... यह कोई पुराना चाल ज्यादातर विधानसभा भाषा में प्रयोग किया जाता है


क्या इससे तेज है != 1?
फिडिंग बिट्स

2
प्राचीन समय में मैनुअल असेंबली ऑप्टिमाइजेशन (x86) करते समय अगर मुझे सही से याद हो कि xorएप्रोच में कम मशीन कोड होता है और उसे संबंधित असाइनमेंट की तुलना में तेजी से निष्पादित किया जाता है 0... हालाँकि इस प्रश्न में एक xorऔर एक तुलना होती है, इसलिए मुझे लगता है कि !=हो सकता है और तेज। मैं हालांकि इतना निश्चित नहीं हूं, इसके लिए कुछ कंपाइलर जेनरेटेड असेंबली देखने की जरूरत होगी।
फेरेंक डेक

10
@BitFiddlingCodeMonkey: नहीं। यदि XOR कुछ देशी स्तर की समानता परीक्षण की तुलना में तेज़ था, तो आपका संकलक XORs को समानता के परीक्षण के लिए उत्सर्जित करेगा। इसलिए, XOR कभी भी संकलक के अनुकूलन पर समानता परीक्षण की तुलना में तेज़ नहीं होते हैं। फास्ट कोड लिखने का नियम 101 है, "संकलक की कोशिश और मदद न करें। आप केवल उस अपठनीय कोड को समाप्त करेंगे जो अभ्यास में धीमा है"।
मैट

@fritzone IIRC, XOR ट्रिक्स में रजिस्टरों को बचाने के लिए अधिक था, एक रजिस्टर लोड बी / सी को बचाने से शाब्दिक को कुछ मामलों में सीधे ओपी में एन्कोड किया जा सकता था, और स्टेटस फ्लैग के साथ कुछ सूक्ष्म अंतर (लेकिन मेरी विधानसभा के अधिकांश) चालू थे। 68k और डीएसपी)।
mpdonadio

1
@MPD: आम तौर पर यह एक रजिस्टर (कम से कम 386+) साफ़ करने के साथ करना है। xor eax, eax, eax को दो बाइट्स में शून्य पर सेट करता है, लेकिन mov eax, 0 में तीन या छह बाइट्स (एन्कोडिंग के आधार पर) लगते हैं, और xor फॉर्म की तुलना में इसे थोड़ा अधिक समय लगता है ।
मैट

18

^ऑपरेटर XOR बिटवाइज़ है। और 0x1संख्या 1, हेक्साडेसिमल स्थिरांक के रूप में लिखा गया है।

तो, x ^ 0x1एक नए मूल्य का मूल्यांकन करता है जो कि जैसा है x, लेकिन कम से कम महत्वपूर्ण बिट फ़्लिप के साथ है।

एक बहुत ही जटिल और अस्पष्ट फैशन में कोड 1 की तुलना में एक्स से अधिक कुछ नहीं करता है।


11

एक या अधिक बिट्स को पलटने के लिए एक्सर (एक्सक्लूसिव या) ऑपरेटर का सबसे अधिक उपयोग किया जाता है। ऑपरेशन यह पूछना है कि क्या वास्तव में बिट्स में से एक है, यह निम्न सत्य तालिका की ओर जाता है (ए और बी इनपुट हैं, वाई आउटपुट है):

A    B    Y
0    0    0
0    1    1
1    0    1
1    1    0

अब इस कोड का उद्देश्य यह जांचना प्रतीत होता है कि क्या अंतिम रूप से 1 बिट है, और अन्य 0 हैं, यह बराबर है if ( x != 1 )। इस अस्पष्ट विधि का कारण यह हो सकता है कि पूर्व बिट हेरफेर तकनीक का उपयोग किया गया है और शायद कार्यक्रम में अन्य स्थानों पर उपयोग किया जाता है।


8

^में बिटवाइस xor operatorहै c। आपके मामले में x 1 के साथ xor'ed है। उदाहरण xके लिए मान 10 है, तो 10d ^ 1d ===> 1010b ^ 0001b = 1011b, 1011b == 11dस्थिति सही हो जाती है।


अपने उत्तर में टाइपो। 10 != 1010
फिडिंग बिट्स

@BitFiddlingCodeMonkey: अपनी टिप्पणी में टाइपो:10 (decimal) == 1010 (binary)
पॉल आर

6
@PaRR किसी को कैसे पता होना चाहिए कि दशमलव क्या है और अगर आप bवहां कुछ नहीं डालते हैं तो क्या बाइनरी है ?
फिडिंग बिट्स

0b1010 चीजों को करने का पायथोनिक तरीका नहीं होगा?
टैंकरस्मैश

8

बिटवाइज़ टेस्ट एक जानबूझकर आक्षेप है, लेकिन अगर अंतर्निहित डेटा एक आईबीएम मेनफ्रेम सिस्टम से कॉर्पोरेट डेटा है, तो बस यह हो सकता है कि मूल दस्तावेज को प्रतिबिंबित करने के लिए कोड लिखा गया था। आईबीएम डेटा प्रारूप 1960 में वापस जाते हैं और अक्सर भंडारण को बचाने के लिए एक शब्द के भीतर एकल बिट्स के रूप में झंडे को एनकोड करते हैं। जैसा कि स्वरूपों को संशोधित किया गया था, फ्लैग बाइट्स को मौजूदा रिकॉर्ड के अंत में पीछे की ओर संगतता बनाए रखने के लिए जोड़ा गया था। उदाहरण के लिए, SMF रिकॉर्ड के लिए दस्तावेज़ीकरण, एक एकल रिकॉर्ड में तीन अलग-अलग शब्दों के भीतर तीन अलग-अलग बिट्स का परीक्षण करने के लिए असेंबली भाषा कोड दिखा सकता है ताकि यह तय किया जा सके कि डेटा एक इनपुट फ़ाइल थी। मैं टीसीपी / आईपी इंटर्नल के बारे में बहुत कम जानता हूं, लेकिन आपको वहां भी झंडे मिल सकते हैं।


7

ऑपरेटर ^ बिटवाइज़-एक्सर (देखें और;)। एक बिट जोड़ी के लिए परिणाम है,

0 ^ 0 == 0
0 ^ 1 == 1
1 ^ 0 == 1
1 ^ 1 == 0

तो अभिव्यक्ति,

( x ^ 0x1 )

inverts / x के 0 वें बिट को फ़्लिप करता है (अन्य बिट्स को अपरिवर्तित छोड़कर)।

विचार करें कि क्या x में 0x0 और 0x1 के अलावा मान हो सकते हैं? जब x एक एकल बिट फ़ील्ड होता है, तो इसमें केवल 0x0 और 0x1 मान हो सकते हैं, लेकिन जब x एक int (char / short / long / etc) होता है, तो bit0 के अलावा बिट्स अभिव्यक्ति के परिणाम को प्रभावित कर सकते हैं।

दी गई अभिव्यक्ति बिट्स के साथ बिट्स को परिणाम को प्रभावित करने की अनुमति देती है,

if ( 0 != ( x ^ 0x1 ) )

जो इस (सरल) अभिव्यक्ति के बराबर सत्यता है,

if ( x ^ 0x1 )

ध्यान दें कि यह अभिव्यक्ति केवल बिट 0 की जांच करेगी,

if( 0x1 & ( x ^ 0x1 ) )

तो जैसा कि प्रस्तुत किया गया है अभिव्यक्ति वास्तव में दो अभिव्यक्ति चेक का संयोजन है,

if( ( x & ~0x1 )  //look at all bits besides bit0
||  ( x ^ 0x1 ) ) //combine with the xor expression for bit0

क्या लेखक ने केवल बिट 0 की जांच करने का इरादा किया है, और इस अभिव्यक्ति का उपयोग करने का मतलब है,

if( 0x1 & ( x ^ 0x1 ) )

या लेखक ने bit1-bitN और x0 के xor के मानों को प्राप्त करने का इरादा किया है?


7

मैं एक नया उत्तर जोड़ रहा हूं क्योंकि किसी ने वास्तव में नहीं बताया कि उत्तर को सहज रूप से कैसे प्राप्त किया जाए।

का विलोम +है -
का विलोम ^है ^

आप कैसे हल 0 != x - 1करते हैं x? आप + 1दोनों पक्षों के लिए: 0 + 1 != x - 1 + 11 != x
आप कैसे हल 0 != x ^ 1करते हैं x? आप ^ 1दोनों पक्षों के लिए: 0 ^ 1 != x ^ 1 ^ 11 != x


6

मुझे लगता है कि अन्य बिट्स या बिट-फील्ड मान हैं x, और यह परीक्षण करने का इरादा है कि केवल कम-ऑर्डर बिट सेट है। संदर्भ में, मुझे लगता है कि यह डिफ़ॉल्ट है, और इसलिए इस और कुछ संबंधित m(शायद सांकेतिक शब्दों में बदलना करने के लिए अधिक महंगा) के एन्कोडिंग को छोड़ दिया जा सकता है, क्योंकि वे दोनों एक डिफ़ॉल्ट मान होना चाहिए, एक निर्माता या समान में आरंभीकृत।

किसी तरह डिकोडर को यह पता लगाने में सक्षम होना चाहिए कि ये मान गायब हैं। यदि वे किसी संरचना के अंत में हैं, तो यह एक ऐसे lengthमूल्य के माध्यम से संप्रेषित किया जा सकता है जो हमेशा मौजूद होता है।


4

XOR C # फ्लैग एनम में उपयोगी है। ईनम मान से एकल ध्वज को हटाने के लिए, एक्सर ऑपरेटर ( यहां संदर्भ ) का उपयोग करना आवश्यक है

उदाहरण:

[Flags]
enum FlagTest { None 0x0, Test1 0x1, Test2 0x2, Test3 0x4}

FlagTest test = FlagTest.Test2 | FlagTest.Test3;
Console.WriteLine(test); //Out: FlagTest.Test2 | FlagTest.Test3
test = test ^ FlagTest.Test2;
Console.WriteLine(test); //Out: FlagTest.Test3

लेकिन सवाल C ++ के बारे में है, C # के बारे में नहीं है
TheDmi

@ अन्य: बिट हेरफेर और बिटमास्क के बारे में भी। C # में ध्वज पताका निश्चित रूप से बिटमास्क के बारे में है।
इग्रेक।

साथ ही यह C ++ में भी उपयोगी हो सकता है। देखें: स्टैक 1 और स्टैक 2
इग्रेक।

यह उत्तर मूल प्रश्न के साथ कुछ भी नहीं लगता है, बिटकॉइन XOR ऑपरेटर की कुछ चर्चा से इतर?
पॉल आर

4

बहुत सारे अच्छे उत्तर हैं, लेकिन मैं इसे सरल तरीके से सोचना पसंद करता हूं।

if ( 0 != ( x ^ 0x1 ) );

सबसे पहले। यदि तर्क शून्य है तो केवल कथन गलत है। इसका मतलब यह है कि शून्य के बराबर की तुलना करना व्यर्थ है।

if ( a != 0 );
// Same as
if ( a );

ताकि हमें छोड़ दिया जाए:

if ( x ^ 0x1 );

एक XOR एक के साथ। XOR जो करता है वह अनिवार्य रूप से बिट्स का पता लगाता है जो अलग-अलग होते हैं। इसलिए, यदि सभी बिट्स समान हैं, तो यह 0. वापस आ जाएगा। 0 चूंकि झूठा है, केवल उसी समय यह झूठा वापस आएगा यदि सभी बिट समान हैं। तो यह झूठा होगा यदि तर्क समान हैं, अगर वे अलग हैं तो सच है ... बस ऑपरेटर के बराबर नहीं

if ( x != 0x1 );

यदि वास्तव में, दोनों के बीच एकमात्र अंतर यह है कि !=0 या 1 ^वापस आएगा , जबकि कोई भी संख्या लौटाएगा , लेकिन परिणाम की सत्यता हमेशा एक ही होगी। इसके बारे में सोचने का एक आसान तरीका है।

(b != c) === !!(b ^ c) // for all b and c

अंतिम "सरलीकरण" 0x1दशमलव में परिवर्तित हो रहा है जो 1. है। इसलिए आपका कथन इसके समकक्ष है:

if ( x != 1 )

1

^ एक बिटवाइज़ XOR ऑपरेटर है

यदि x = 1

          00000001   (x)       (decimal 1)
          00000001   (0x1)     (decimal 1)
XOR       00000000   (0x0)     (decimal 0)

यहाँ 0 == (x ^ 0x1)

यदि x = 0

          00000000   (x)       (decimal 0)
          00000001   (0x1)     (decimal 1)
XOR       00000001   (0x1)     (decimal 0)

यहाँ 0! = (x ^ 0x1)

एक xor b की सत्य तालिका:

a           b        a xor b
----------------------------
1           1           0
1           0           1
0           1           1
0           0           0

कोड का सीधा सा मतलब है


6
क्या वास्तव में एक और डुप्लिकेट उत्तर पोस्ट करना आवश्यक है?
रहस्यपूर्ण निर्णय

2
आप एक और उत्तर कह सकते हैं लेकिन डुप्लिकेट नहीं। क्षमा करें यदि आप बुरा
मानते

1

मानक तकनीक का उपयोग किया जा सकता है, यहाँ, एक मुहावरे को दोहराना है क्योंकि यह स्पष्टता के लिए आस-पास के संदर्भ में प्रकट होता है, बजाय इसके कि इसे एक मुहावरे के साथ प्रतिस्थापित करके, जो अंकगणितीय रूप से सरल लेकिन संदर्भहीन व्यर्थ है।

आसपास का कोड बार-बार संदर्भ दे सकता है (x ^ 1), या परीक्षण पूछ सकता है "यदि बिट 0 अन्य तरह से चारों ओर था, तो क्या यह बिट-मास्क खाली होगा?"।

यह देखते हुए कि स्थिति कुछ encode()एड होने का कारण बनती है , ऐसा हो सकता है कि संदर्भ में बिट 0 की डिफ़ॉल्ट स्थिति अन्य कारकों द्वारा उलट दी गई है, और हमें केवल अतिरिक्त जानकारी को एनकोड करने की आवश्यकता है यदि बिट्स में से कोई भी डिफॉल्ट (सामान्य रूप से सभी-शून्य) )।

यदि आप अभिव्यक्ति को संदर्भ से बाहर ले जाते हैं और पूछते हैं कि यह क्या करता है, तो आप अंतर्निहित इरादे की अनदेखी करते हैं। आप बस कंपाइलर से असेंबली आउटपुट को देख सकते हैं और देख सकते हैं कि यह केवल 1 के साथ प्रत्यक्ष समानता की तुलना करता है।


0

जैसा कि मैं देख रहा हूं कि उत्तर अब तक निपटने के लिए एक सरल नियम है XOR एस से । विवरण में क्या ^और क्या 0xमतलब है (और if, और !=आदि) के बिना, 0 != (x^1)इस तथ्य का उपयोग करते हुए अभिव्यक्ति को फिर से काम किया जा सकता है (a^a)==0:

0 != (x^1) <=> [xor left and right side by 1]
(0^1) != (x^1^1) <=>
1 != x
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.