जब एक अभिव्यक्ति से पहले एक टिल्ड क्या करता है?


195
var attr = ~'input,textarea'.indexOf( target.tagName.toLowerCase() )
           ? 'value'
           : 'innerHTML'

मैंने इसे एक उत्तर में देखा, और मैंने इसे पहले कभी नहीं देखा।

इसका क्या मतलब है?


जवाबों:


267

~एक बिटवाइज़ ऑपरेटर है जो अपने ऑपरेंड में सभी बिट्स को फ़्लिप करता है।

उदाहरण के लिए, यदि आपका नंबर था 1, तो आईईईई 754 फ्लोट (कैसे जावास्क्रिप्ट संख्याओं का इलाज करता है) का द्विआधारी प्रतिनिधित्व होगा ...

0011 1111 1111 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000

तो ~अपने ऑपरेंड को 32 बिट पूर्णांक (बिटकॉइन ऑपरेटरों को जावास्क्रिप्ट में करते हैं) में कनवर्ट करता है ...

0000 0000 0000 0000 0000 0000 0000 0001

यदि यह एक नकारात्मक संख्या थी, तो इसे 2 के पूरक में संग्रहीत किया जाएगा: सभी बिट्स को उल्टा करें और 1 जोड़ें।

… और फिर उसके सारे चूतड़ झड़ जाते हैं…

1111 1111 1111 1111 1111 1111 1111 1110

तो इसका उपयोग क्या है, फिर? जब कोई इसका इस्तेमाल कर सकता है?

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

यह भी एक (आमतौर पर) स्पष्ट नहीं है कि चाल चालू करने के लिए indexOf()'एस मिल गया में वापसी मान truthy (जबकि जिससे नहीं मिला के रूप में falsy ) और लोगों को अक्सर यह दोगुना होकर 32 बिट करने के लिए संख्या छोटा (और उसके दशमलव स्थान छोड़ने के अपने पक्ष प्रभाव के लिए इसका इस्तेमाल करते हैं, प्रभावी रूप Math.floor()से सकारात्मक संख्याओं के लिए समान )।

मैं अस्पष्ट कहता हूं क्योंकि यह तुरंत स्पष्ट नहीं है कि इसका उपयोग किस लिए किया जा रहा है। आम तौर पर, आप चाहते हैं कि आपका कोड इसे पढ़ने वाले अन्य लोगों से स्पष्ट रूप से संवाद करे। जबकि उपयोग शांत लग~ सकता है , यह आमतौर पर अपने स्वयं के अच्छे के लिए बहुत चालाक है। :)

यह अब भी कम प्रासंगिक है कि जावास्क्रिप्ट Array.prototype.includes()और है String.prototype.includes()। ये एक बूलियन मान लौटाते हैं। यदि आपका लक्ष्य प्लेटफ़ॉर्म इसका समर्थन करता है, तो आपको स्ट्रिंग या सरणी में मान के अस्तित्व के परीक्षण के लिए इसे पसंद करना चाहिए।


2
क्या गंदा सही शब्द है? अगर यह काम करता है तो मैं इसे भाषा का एक मुहावरा कहूंगा। कई मुहावरे हैं। एक बार जब आप उन्हें सीख लेते हैं तो वे अस्पष्ट नहीं होते हैं। पायथन में सूची की समझ स्पष्ट नहीं है यदि आप उन्हें नहीं जानते हैं और अधिक क्रिया छोरों के साथ पूरा किया जा सकता है लेकिन आप पायथन प्रोग्रामर को कभी भी उनका उपयोग नहीं करने के लिए कहेंगे। इसी तरह value = value || defaultजावास्क्रिप्ट में एक सामान्य और मान्य मुहावरा है जब तक आप जानते हैं कि आप कब और इसका उपयोग नहीं कर सकते हैं।
शाम

3
@ मुझे लगता है कि यह वास्तव में कोई फर्क नहीं पड़ता कि कोई इसका उपयोग करता है या नहीं। मुझे लगता है कि सूची की समझ (भाषा सुविधा) की तुलना करना वास्तव में एक ही बात नहीं है ( कुछ अतिरिक्त वर्ण टाइप करने से बचने का चतुर तरीका)। यदि आपको लगता है कि बुरा शब्द बहुत कठोर है, तो कृपया मेरे उत्तर को संपादित करने के लिए स्वतंत्र महसूस करें।
एलेक्स

2
शायद एक अधिक सामान्य उदाहरण है v = t ? a : b;। मुझे लगता है कि var v; if (t} { v = a; } else { v = b; }आम तौर पर 5+ रेखाओं से अधिक टूटी हुई और उससे भी अधिक स्पष्ट होती है, var v = b; if (t) { v = a; }जिसकी तुलना में आमतौर पर 4+ लाइनें होती हैं। लेकिन मुझे पता है कि बहुत से लोग ? :ऑपरेटरों से परिचित नहीं हैं जो दूसरे या तीसरे तरीके को पसंद करेंगे। मुझे लगता है कि पहला अधिक पठनीय है। मैं सामान्य सिद्धांत से सहमत हूं, कोड को स्पष्ट करें, हैक का उपयोग न करें। मुझे लगता है कि मैंने ~v.indexOf('...')इसे सीख लेने के बाद बस बहुत स्पष्ट होना देखा है।
gman

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

3
मैं ~मुहावरेदार नहीं कहूंगा । यह तकनीकी रूप से भाषा युक्ति का हिस्सा है , लेकिन यह सामान्य उपयोग में भाषा का इतना हिस्सा नहीं है ।
कृ

109

किसी indexOf()अभिव्यक्ति के प्रभावी ढंग से उपयोग करने से आपको सीधे संख्यात्मक सूचकांक के बजाय एक सत्य / गलत परिणाम मिलता है।

यदि वापसी मान है -1, तो ~-1है 0क्योंकि -1सभी 1 बिट्स की एक श्रृंखला है। शून्य से अधिक या उसके बराबर कोई भी मान गैर-शून्य परिणाम देगा। इस प्रकार,

if (~someString.indexOf(something)) {
}

ifकोड को चलाने का कारण होगा जब "कुछ" "someString" में होगा। यदि आप .indexOf()सीधे बूलियन के रूप में उपयोग करने का प्रयास करते हैं, तो वह काम नहीं करेगा क्योंकि कभी-कभी यह शून्य (जब "कुछ" स्ट्रिंग की शुरुआत में होता है) लौटता है।

बेशक, यह भी काम करता है:

if (someString.indexOf(something) >= 0) {
}

और यह काफी कम रहस्यमय है।

कभी-कभी आप यह भी देखेंगे:

var i = ~~something;

~दो बार ऑपरेटर का उपयोग करना एक स्ट्रिंग को 32-बिट पूर्णांक में बदलने का एक त्वरित तरीका है। पहला ~रूपांतरण करता है, और दूसरा ~बिट्स को वापस फ़्लिप करता है। बेशक, यदि ऑपरेटर ऐसी चीज़ पर लागू होता है जिसे किसी संख्या में परिवर्तित नहीं किया जा सकता है, तो आप NaNपरिणाम के रूप में प्राप्त करते हैं । ( संपादित करें - वास्तव में यह दूसरा ~है जिसे पहले लागू किया गया है, लेकिन आपको यह विचार मिलता है।)


2
उन लोगों के लिए जो बिट द्वारा नकारात्मक को कम नहीं करना चाहते हैं, ~जब पूर्णांकों पर प्रदर्शन किया जाता है -(x + 1)
फाबेरियो मट्टे सेप

ऐसा लगता है, ठीक है, आप जानते हैं, नकारात्मक संख्यात्मक मानों को नकारात्मक बूलियन को पहले स्थान पर वापस करना चाहिए। लेकिन जेएस की एक और असफलता, मुझे लगता है?
वावाव

7
@adlwalrus अच्छी तरह से 0होने की परंपरा है falseऔर गैर-शून्य होने की trueतारीखें वापस आती हैं, कम से कम 'सी' में 70 के दशक की और शायद बहुत सारी अन्य तत्कालीन सिस्टम प्रोग्रामिंग भाषाओं की। यह शायद हार्डवेयर के काम करने के तरीके से उपजा है; बहुत सारे CPU एक ऑपरेशन के बाद एक शून्य बिट सेट करते हैं, और इसका परीक्षण करने के लिए एक संबंधित शाखा निर्देश है।
पॉइंटर

4
इसे 32 बिट इंट में बदलने का एक तेज़ तरीका होगा | 0, जिस स्थिति में इसका केवल एक ही ऑपरेशन होगा।
एलेक्स

@alex वास्तव में, हालांकि हम जरूरी रनटाइम पर भरोसा नहीं कर सकते हैं कि ~~बिल्कुल उसी तरह से एक सरल अनुप्रयोग की व्याख्या न करें ।
नुकीले

29

~है बिटवाइस नहीं ऑपरेटर , ~xके रूप में लगभग एक ही है -(x+1)। इसे समझना आसान है। इसलिए:

~2;    // -(2+1) ==> -3

विचार करें -(x+1)-1उत्पादन करने के लिए उस ऑपरेशन का प्रदर्शन कर सकते हैं 0

दूसरे शब्दों में, ~संख्या मानों की एक सीमा के साथ उपयोग करने falseपर 0केवल -1इनपुट मूल्य के लिए एक मिथ्या (मोटे से लेकर ) मूल्य का उत्पादन होगा , अन्यथा, किसी भी अन्य सत्य मूल्य।

जैसा कि हम जानते हैं, -1आमतौर पर प्रहरी मूल्य कहा जाता है । इसका उपयोग कई कार्यों के लिए किया जाता है जो सफलता के लिए और C भाषा में विफलता के लिए >= 0मान लौटाते हैं। जावास्क्रिप्ट में वापसी के मूल्य का वही नियम है ।-1indexOf()

इस तरह से दूसरे स्ट्रिंग में एक विकल्प की उपस्थिति / अनुपस्थिति की जांच करना आम है

var a = "Hello Baby";

if (a.indexOf("Ba") >= 0) {
    // found it
}
if (a.indexOf("Ba") != -1) { 
    // found it
}

if (a.indexOf("aB") < 0) { 
    // not found
}
if (a.indexOf( "aB" ) == -1) { 
    // not found
}

हालांकि, इसे ~नीचे के माध्यम से करना अधिक आसानी से होगा

var a = "Hello Baby";

~a.indexOf("Ba");         // -7   -> truthy
if (~a.indexOf("Ba")) {   // true
    // found it
}

~a.indexOf("aB");         // 0    -> falsy
!~a.indexOf("aB");        // true
if (!~a.indexOf( "aB" )) {  // true
    // not found
}

तुम्हें पता नहीं है जेएस: प्रकार और व्याकरण काइल सिम्पसन द्वारा


1
यह निश्चित रूप से अंकित मूल्य पर समझना आसान है, भले ही कोई व्यक्ति उस पृष्ठभूमि को नहीं समझता है जो इसे काम करता है। -(x+1)अगर मैं इसे एक बयान में देखा तो मैं दूसरी बार देखूंगा। टिल्ड मुझे बताता है कि जावास्क्रिप्ट की 0-प्रकृति के लिए क्षतिपूर्ति करने के लिए वह क्या कर रहा है। इसके अलावा, कम कोष्ठक पढ़ने के लिए बेहतर है
नियमित जो

अपने शुरुआती चेक कोड ब्लॉक में आप कम से कम टाइप कर सकते हैं if (a.indexOf("Ba") > -1) {// found} //true, हालांकि टिल्ड उदाहरणों की तुलना में थोड़ा लंबा, आपके द्वारा दिए गए दो उदाहरणों और नए प्रोग्रामर के लिए काफी कम है var opinion = !~-1 ? 'more' : 'less'
हॉफमेन

24

~indexOf(item) बहुत बार आता है, और यहाँ के उत्तर बहुत अच्छे हैं, लेकिन शायद कुछ लोगों को यह जानने की ज़रूरत है कि इसका उपयोग कैसे करें और सिद्धांत को "छोड़ें":

   if (~list.indexOf(item)) {
     // item in list
   } else {
     // item *not* in list
   }

1
मैं सहमत हूँ। Airbnb जावास्क्रिप्ट स्टाइल गाइड को अस्वीकार कर देता है ++और --क्योंकि वे "अत्यधिक चालाकी को प्रोत्साहित करते हैं" और फिर भी किसी तरह ~बच गए (छाया में
दुबके हुए

@ शांमल यह विकल्प है list.indexOf(item) >= 0या ... > -1चूंकि जावास्क्रिप्ट शून्य-आधारित है और इसे शुरू से ही संबोधित नहीं करना है। इसके अलावा, सिर्फ राय (एयरबीएनबी के रूप में), कोई भी जो जावास्क्रिप्ट में कुछ भी सार्थक कर रहा है वह जानता है ++, और जबकि --कम आम है, अर्थ का अनुमान लगाया जा सकता है।
नियमित जो

@RegularJoe मैं उस सबसे सहमत हूं। मुझे व्यक्तिगत रूप से जरूरत नहीं है ++और --आदिम तरीकों की वजह से थोड़ी देर में map, forEachआदि मेरी बात और है कि जब उन्होंने ~मानक का उपयोग और वेतन वृद्धि संचालकों को शामिल नहीं किया तो वे अत्यधिक मुश्किल क्यों नहीं समझे । कुछ करने से मना करने पर CIS101 का कोई मतलब नहीं है।
शनीमल

11

एक परिणाम से एक सत्य मूल्य बनाने के लिए टिल्ड ट्रिक का उपयोग करने पर विचार करने वालों के लिए indexOf, यह अधिक स्पष्ट है और इसके बजाय includesविधि काString उपयोग करने के लिए कम जादू है ।

'hello world'.includes('hello') //=> true
'hello world'.includes('kittens') //=> false

ध्यान दें कि यह ईएस 2015 के रूप में एक नया मानक तरीका है इसलिए यह पुराने ब्राउज़रों पर काम नहीं करेगा। ऐसे मामलों में जहां यह मायने रखता है, String.prototype.includes polyfill का उपयोग करने पर विचार करें ।

समान सिंटैक्स का उपयोग करके सरणियों के लिए भी यह सुविधा उपलब्ध है :

['apples', 'oranges', 'cherries'].includes('apples') //=> true
['apples', 'oranges', 'cherries'].includes('unicorns') //=> false

यदि आपको पुराने ब्राउज़र समर्थन की आवश्यकता है तो यहां Array.prototype.includes पॉलीफ़िल है।


2
शामिल करने से बचें ()। यह लिखने के समय IE (किसी भी पुराने ब्राउज़र नहीं) के किसी भी संस्करण में समर्थित नहीं है: developer.mozilla.org/en/docs/Web/JavaScript/Reference/…
Onshop

8
या सिर्फ एक संकलक का उपयोग करें, ताकि आप स्पष्ट कोड लिख सकें, बजाय सबसे खराब सामान्य भाजक जेएस दुभाषिया के अनुसार भाषा लिखने के लिए ...
काइल बेकर

2
@ सही है, यह नेटस्केप 4.72 में भी काम नहीं करता है।
मीकमेकाना जूल
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.