“ | =” หมายถึงอะไร (ผู้ประกอบการท่อเท่ากับ)


249

ฉันลองค้นหาโดยใช้ Google Search และ Stack Overflow แต่มันไม่แสดงผลลัพธ์ใด ๆ ฉันเคยเห็นสิ่งนี้ในรหัสห้องสมุด opensource:

Notification notification = new Notification(icon, tickerText, when);
notification.defaults |= Notification.DEFAULT_SOUND;
notification.defaults |= Notification.DEFAULT_VIBRATE;

"| =" ( pipe equal operator) หมายถึงอะไร


4
ฉันสงสัยว่าการเพิ่มบางอย่างเช่นpipe equal operatorคำถามนี้หรือเอกสารอื่น ๆ ในหัวข้อจะไม่ช่วยให้ผู้คนค้นหา
Denys Séguret

10
@EJP พวกคุณกำลังพูดถึงเอกสารนี้ มันบอกชัดเจนว่าเอกสารขาดเอกสารเกี่ยวกับการใช้สิ่งนี้
wtsang02

36
นอกจากว่าคุณรู้ว่ามันถูกเรียกว่า pipe เท่ากับมันเป็นการยากที่จะค้นหาโดยไม่ถามใครสักคน
ataulm

@ataulm แน่นอนใช้เวลาไปเที่ยวรอบ ๆ เพื่อหาคำvertical barที่ท้ายที่สุดก็พาฉันมาที่นี่
ruuter

1
ซ้ำซ้อนที่เป็นไปได้ของตัวดำเนินการ | = ทำอะไรใน Java?
poring91

คำตอบ:


323

|=+=อ่านแบบเดียวกับที่

notification.defaults |= Notification.DEFAULT_SOUND;

เป็นเช่นเดียวกับ

notification.defaults = notification.defaults | Notification.DEFAULT_SOUND;

ที่|เป็นบิตฉลาดหรือผู้ประกอบการ

ผู้ประกอบการทั้งหมดที่มีการอ้างอิงที่นี่

ตัวดำเนินการบิตที่ชาญฉลาดถูกใช้เนื่องจากตามปกติค่าคงเหล่านั้นจะเปิดใช้งาน int เพื่อดำเนินการตั้งค่าสถานะ

หากคุณดูค่าคงที่เหล่านั้นคุณจะเห็นว่ามันอยู่ในอำนาจของสอง:

public static final int DEFAULT_SOUND = 1;
public static final int DEFAULT_VIBRATE = 2; // is the same than 1<<1 or 10 in binary
public static final int DEFAULT_LIGHTS = 4; // is the same than 1<<2 or 100 in binary

ดังนั้นคุณสามารถใช้บิตฉลาดหรือเพื่อเพิ่มธง

int myFlags = DEFAULT_SOUND | DEFAULT_VIBRATE; // same as 001 | 010, producing 011

ดังนั้น

myFlags |= DEFAULT_LIGHTS;

หมายถึงเราเพิ่มธง

และสมมาตรเราทดสอบการตั้งค่าสถานะโดยใช้&:

boolean hasVibrate = (DEFAULT_VIBRATE & myFlags) != 0;

2
เช่นเดียวกับเป็นเช่นเดียวกับj += 1; j = j + 1;
David Schwartz

1
@ ARS: ฉันไม่สามารถนึกถึงตัวอย่างในภาษาจาวา (อาจjจะvolatileใช่มั้ย) แต่ฉันจะเอาคำพูดของคุณไปใช้
David Schwartz

6
@DavidSchwartz ดูสิ่งนี้
arshajii

2
boolean hasVibrate = DEFAULT_VIBRATE & myFlags;- คุณแปลจากintเป็นbooleanอย่างนั้นใน Java ได้ไหม ที่จะถูกต้องใน C แต่ฉันคิดว่าใน Java จะต้องมีการเขียนเป็นboolean hasVibrate = ((DEFAULT_VIBRATE & myFlags) == DEFAULT_VIBRATE);
BlueRaja - Danny Pflughoeft

1
@DavidSchwartz ว้าวการเปรียบเทียบกับ+=ในที่สุดก็หลอกให้ฉันเข้าใจ ขอบคุณ!
C4d

39

คุณได้รับคำตอบที่เพียงพอสำหรับคำถามของคุณ แต่อาจเป็นคำตอบของฉันช่วยให้คุณเพิ่มเติมเกี่ยวกับ|=ชนิดของผู้ประกอบการไบนารี

ฉันกำลังเขียนตารางสำหรับตัวดำเนินการระดับบิต : การ
ติดตามที่ถูกต้อง:

----------------------------------------------------------------------------------------
Operator   Description                                   Example
----------------------------------------------------------------------------------------
|=        bitwise inclusive OR and assignment operator   C |= 2 is same as C = C | 2
^=        bitwise exclusive OR and assignment operator   C ^= 2 is same as C = C ^ 2
&=        Bitwise AND assignment operator                C &= 2 is same as C = C & 2
<<=       Left shift AND assignment operator             C <<= 2 is same as C = C << 2
>>=       Right shift AND assignment operator            C >>= 2 is same as C = C >> 2  
----------------------------------------------------------------------------------------

หมายเหตุผู้ประกอบการทั้งหมดเป็นผู้ประกอบการแบบไบนารี

นอกจากนี้ยังมีหมายเหตุ: (สำหรับด้านล่างจุดที่ผมอยากจะเพิ่มคำตอบของฉัน)

  • >>>เป็นตัวดำเนินการระดับบิตใน Java ที่เรียกว่าUnsigned shift
    แต่ >>>=ไม่ใช่โอเปอเรเตอร์ใน Java >>> = ผู้ประกอบการ

  • ~เป็นบิตประกอบบิตบิต0 to 1 and 1 to 0(ตัวดำเนินการ Unary) แต่~=ไม่ใช่ตัวดำเนินการ

  • นอกจากนี้ !Called Logical NOT Operator แต่!=ตรวจสอบว่าค่าของตัวถูกดำเนินการสองค่าเท่ากันหรือไม่หากค่าไม่เท่ากันเงื่อนไขจะกลายเป็นจริง (A != B) is trueเช่น ขณะที่A=!Bหมายความว่าถ้าBเป็นtrueแล้วAจะกลายเป็นfalse(และถ้าBเป็นfalseแล้วAจะกลายเป็นtrue)

หมายเหตุด้านข้าง: |ไม่ได้เรียกว่าไปป์แทนที่จะเรียกว่าหรือไปป์เป็นคำศัพท์ของเชลล์ถ่ายโอนกระบวนการหนึ่งไปยังกระบวนการถัดไป ..


9
ฉันรู้สึกว่า "ไพพ์" เป็นชื่อของตัวละครซึ่งเป็นที่มาของคำว่าเชลล์ แต่เมื่อมองไปที่ Wikipedia จริงๆแล้วมันเรียกว่า "บาร์แนวตั้ง" และ "ไพพ์" นั้นเป็นคำสั่งเฉพาะของเชลล์ แค่อยากจะบอกว่าขอบคุณสำหรับการเพิ่มข้อความด้านข้าง!
Caleb Brinkman

18

ฉันกำลังมองหาคำตอบว่าอะไร|=ใน Groovy และถึงแม้ว่าคำตอบข้างต้นจะอยู่ที่พวกเขาไม่ได้ช่วยให้ฉันเข้าใจรหัสเฉพาะที่ฉันกำลังดูอยู่

โดยเฉพาะอย่างยิ่งเมื่อนำไปใช้กับตัวแปรบูลีน "| =" จะตั้งค่าเป็น TRUE เป็นครั้งแรกที่พบนิพจน์ความจริงทางด้านขวาและจะถือค่า TRUE สำหรับ | | ที่ตามมาทั้งหมด เหมือนสลัก

นี่คือตัวอย่างแบบง่าย ๆ ของสิ่งนี้:

groovy> boolean result  
groovy> //------------ 
groovy> println result           //<-- False by default
groovy> println result |= false 
groovy> println result |= true   //<-- set to True and latched on to it
groovy> println result |= false 

เอาท์พุท:

false
false
true
true

แก้ไข : เหตุใดจึงมีประโยชน์นี้

พิจารณาสถานการณ์ที่คุณต้องการทราบว่ามีอะไรเปลี่ยนแปลงในวัตถุที่หลากหลายหรือไม่และหากเป็นเช่นนั้นให้แจ้งการเปลี่ยนแปลงบางอย่าง ดังนั้นคุณจะตั้งค่าhasChangesบูลีนและตั้งค่าเป็น |= diff (a,b)แล้ว|= dif(b,c)เป็นต้นนี่คือตัวอย่างสั้น ๆ :

groovy> boolean hasChanges, a, b, c, d 
groovy> diff = {x,y -> x!=y}  
groovy> hasChanges |= diff(a,b) 
groovy> hasChanges |= diff(b,c) 
groovy> hasChanges |= diff(true,false) 
groovy> hasChanges |= diff(c,d) 
groovy> hasChanges 

Result: true

10
ใช่ถือเหมือนกันใน Java แต่มันก็เป็นที่น่าสังเกตว่าการดำเนินการดังกล่าวหรือการดำเนินการไม่ได้y|=exprเป็นไฟฟ้าลัดวงจร (ไม่เหมือนy = y || expr) ซึ่งหมายถึงการexprประเมินเสมอ นี้ไม่ได้เป็นที่เห็นได้ชัดสำหรับฉันเป็นครั้งแรก :) ดังนั้นมันจึงเป็นสิ่งสำคัญที่จะต้องทราบก่อน refactoring ทดแทนที่y|=expry=y||xจะไม่เทียบเท่าความหมายในกรณีที่exprจริงมีผลข้างเคียง
NIA

1
และมีในใจนี้ ในกรณีของคุณกับhasChangesมันจะอาจจะดีกว่าที่จะชอบy=y||xรูปแบบที่จะได้รับประโยชน์จากสั้น ciruit เพราะเมื่อคุณพบการเปลี่ยนแปลงใด ๆ มันไม่จำเป็นจริงที่จะทำ diffs susequent เพราะคุณรู้อยู่แล้วว่าคำตอบ (โดยเฉพาะอย่างยิ่งสิ่งสำคัญในสถานการณ์ชีวิตจริงเมื่อเปรียบเทียบวัตถุที่มีความซับซ้อนและการนำเข้าวัตถุdiffเหล่านั้นไม่เร็วนัก)
NIA

@NIA ขอบคุณสำหรับการโหวต ใช่ฉันเห็นด้วยกับประเด็นของคุณเกี่ยวกับการลัดวงจร
dbrin

2
@ FranklinYu แน่นอนว่าไม่ใช่รายละเอียดการใช้งาน การไม่ลัดวงจรไม่ได้กล่าวถึงเฉพาะในสถานที่ที่คุณอ้างถึงเพราะไม่ใช่ลักษณะเฉพาะ - เป็นพฤติกรรมเริ่มต้นและปกติสำหรับผู้ปฏิบัติงานส่วนใหญ่ ความไม่ชอบมาพากลเป็นจริงสั้น circutiness ของ||และ&&และในส่วนที่สอดคล้องกัน15.23และ15.24ของการกำหนดความเป็นจริงนี้จะมีการประกาศอย่างชัดเจนและความแตกต่างนี้จาก|และ&จะเน้น
NIA

2
@ FranklinYu ดังนั้นฉันคิดว่าไม่จำเป็นต้องพูดอะไรเกี่ยวกับเรื่องนี้อีกในส่วนที่คุณอ้างถึง(15.26.2 "ผู้ประกอบการที่ได้รับมอบหมาย Compund") เพียงเพราะการมอบหมาย compond มักจะไม่ลัดวงจร (ไม่มี||=และ&&=ผู้ประกอบการที่จะ ทำผิดกฎและต้องการการกล่าวถึงเป็นพิเศษ)
NIA



3

หมายเหตุ: || = ไม่มีอยู่ (ตรรกะหรือ) คุณสามารถใช้

y= y || expr; // expr is NOT evaluated if y==true

หรือ

y = expr ? true : y;  // expr is always evaluated.

4
ยังไม่เสร็จสมบูรณ์: คุณยังสามารถใช้y |= exprกับบูลีนได้และให้ผลลัพธ์แบบเดียวกันกับyตัวแปรที่มีข้อความสำคัญซึ่งไม่ใช่ curtuit สั้นซึ่งหมายความว่า expr จะได้รับการประเมินเสมอแม้ในกรณีที่y==true
NIA
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.