เวอร์ชันที่เขียนขึ้นของตัวดำเนินการทางตรรกะ


97

นี้เป็นสถานที่เดียวที่ฉันเคยเห็นand, orและnotระบุว่าเป็นผู้ประกอบการที่เกิดขึ้นจริงใน C ++ เมื่อฉันเขียนโปรแกรมทดสอบใน NetBeans ฉันได้ขีดเส้นใต้สีแดงราวกับว่ามีข้อผิดพลาดทางไวยากรณ์และคิดว่าเว็บไซต์ผิด แต่เป็น NetBeans ซึ่งผิดเพราะรวบรวมและทำงานตามที่คาดไว้

ฉันเห็นว่า!เป็นที่ชื่นชอบมากกว่าnotแต่ความสามารถในการอ่านand&& นั้นorดูดีกว่าพี่น้องที่ใช้ไวยากรณ์ของพวกเขา เหตุใดตัวดำเนินการทางตรรกะเวอร์ชันเหล่านี้จึงมีอยู่และเหตุใดจึงดูเหมือนไม่มีใครใช้ C ++ นี้ถูกต้องจริง ๆ หรือมีความเข้ากันได้บางอย่างกับ C ที่มาพร้อมกับภาษาหรือไม่?


4
\ me เขียนโค้ดของเขาใหม่
lmat - คืนสถานะ Monica

2
ด้วยจิตวิญญาณของ "รหัสที่สะอาด" ฉันขอแนะนำเป็นการส่วนตัวให้หลีกเลี่ยงนิสัยการเขียน||และ&&แม้กระทั่ง!ในบางครั้ง คำพูดมักจะดีกว่า "สัญญาณรบกวน" ไม่ต้องพูดถึงความสับสนที่อาจเกิดขึ้นกับตัวดำเนินการจัดการบิต
Ichthyo

2
@Ichthyo นั่นไม่ถูกต้องเสมอไป เป็นวิธีที่เร็วกว่าในการอ่านสัญลักษณ์จำนวนมากและรู้ความหมายของสัญลักษณ์เหล่านี้มากกว่าการอ่านคำศัพท์จำนวนมาก
vallentin

สิ่งที่ชัดเจนสำหรับผู้อ่านที่เป็นมนุษย์ขึ้นอยู่กับ "Gestalt" บางครั้งสัญลักษณ์อาจชัดเจนกว่าคำที่สับสน แต่ในกรณีนี้ไม่ใช่ และคำง่ายๆของภาษาอังกฤษนั้นมีความเป็นสากลมากกว่าสัญลักษณ์พิเศษแปลก ๆ ของภาษาโปรแกรมที่ค่อนข้างแปลกเสียอีก ...
Ichthyo

4
ประชดคำพูดที่andอ่านง่ายกว่าแล้วเขียนว่า " and&& or" แม้ว่า :)
Ivan Vergiliev

คำตอบ:


114

พวกเขามาใน C <iso646.h>ในส่วนหัว ในขณะนั้นมีแป้นพิมพ์ที่ไม่สามารถพิมพ์สัญลักษณ์ที่ต้องการได้&& (ตัวอย่าง) เพื่อให้ส่วนหัวที่มี#define's ที่จะช่วยเหลือพวกเขาในการทำเช่นนั้นโดย (ในตัวอย่างของเรา) กำหนดให้เป็นand &&แน่นอนว่าเมื่อเวลาผ่านไปสิ่งนี้ก็ใช้น้อยลง

ใน C ++ พวกเขากลายเป็นสิ่งที่เรียกว่าราชสกุลอื่น คุณไม่จำเป็นต้องรวมสิ่งใด ๆ เพื่อใช้โทเค็นเหล่านี้ในคอมไพเลอร์ที่เข้ากันได้ (ดังนั้น C ++ - เวอร์ชัน ified ของส่วนหัว C <ciso646>จะว่างเปล่า) โทเค็นสำรองก็เหมือนกับโทเค็นทั่วไปยกเว้นการสะกดคำ ดังนั้นในระหว่างการแยกวิเคราะห์andก็เหมือนกับการ&&สะกดคำที่เหมือนกัน

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

แก้ไข: ฉันเห็นการใช้งานเพิ่มขึ้นเล็กน้อยตั้งแต่โพสต์สิ่งนี้ ฉันยังคงหลีกเลี่ยงพวกเขา


ดังนั้นการตีความโทเค็นทางเลือกเหล่านี้จึงเป็นเพียงคุณสมบัติคอมไพเลอร์หรืออยู่ในข้อกำหนด C ++?
defectivehalt

2
@Kavon: ระบุไว้ในมาตรา 2.5 ของมาตรฐาน มันเป็นคุณสมบัติของภาษา
GManNickG

15
ส่วนตัวคิดว่าดีกว่ามาก ... แต่แล้วฉันก็ลำเอียง ฉันไม่รู้ว่าทำไมบางคนถึงคิดว่าถ้ามันอ่านไม่ออกก็ไม่ใช่รหัส ...
Matthieu M.

ดังนั้นสิ่งเหล่านี้จึงใช้ไม่ได้ใน C โดยไม่รวมไฟล์ส่วนหัวนั้น? ฉันแปลกใจที่ทุกคนไม่ได้ใช้สิ่งเหล่านี้ ทำให้ Python อ่านง่ายขึ้นมาก
endolith

1
อย่างน้อย Visual Studio 2015 CTP 6 ไม่ชอบของฉันorหรือnotไม่รวมส่วนหัว
usr1234567

19

มีไว้เพื่อการใช้งาน (การรองรับอักขระในคีย์บอร์ด / การแสดงผล) และความสามารถในการอ่านทั่วไป แต่มีอีกเหตุผลหนึ่งที่เด่นชัดขึ้นในปัจจุบัน เกือบจะไม่มีคำตอบที่นี่ , ที่นี่หรือแม้กระทั่งคำตอบหลักที่นี่อธิบายเหตุผลหลักที่พวกเราหลายคนชอบเวอร์ชันคำมากกว่าเวอร์ชันสัญลักษณ์ (และเหตุผลหลักที่ภาษาอื่นใช้): ข้อบกพร่อง ความแตกต่างระหว่างเวอร์ชันของคำนั้นสามารถมองเห็นได้ชัดเจน ความแตกต่างระหว่างเวอร์ชันสัญลักษณ์มีน้อยกว่าอย่างเห็นได้ชัดจนถึงจุดที่ทำให้จุดบกพร่องที่น่าดึงดูดในระดับที่สูงกว่ามาก: "x | y" ไม่ใช่ "x || y" มากนัก แต่เมื่อฝังอยู่ในนิพจน์ที่ใหญ่กว่าพวกเราหลายคน พลาดความแตกต่าง คล้ายกับการผสมโดยบังเอิญของตัวดำเนินการมอบหมายกับตัวดำเนินการความเท่าเทียมกัน ด้วยเหตุนี้ฉันจึงหย่านมตัวเองจากเวอร์ชันสัญลักษณ์ (ไม่ใช่เรื่องง่าย) เพื่อสนับสนุนเวอร์ชันคำ ฉันอยากจะให้ใครสักคนสองครั้งกับพวกเขาเนื่องจากความรักในสิ่งเก่า ๆ มากกว่าการล่อลวงโรคจิต


4
น่าเสียดายที่ใน Visual Studio (ณ VS2013) คุณต้องตั้งค่าตัวเลือกคอมไพเลอร์เฉพาะ ( /Za) เพื่อรองรับคำหลักทางเลือก (ดูstackoverflow.com/a/555524/368896 ) ที่น่าจะมีผลกระทบอื่น ๆ ดังนั้นใน Visual Studio จึงไม่จำเป็นต้องทำตามคำแนะนำนี้อย่างปลอดภัย
Dan Nissenbaum

FWIW / - เท่าที่ฉันใส่ช่องว่างรอบ ๆ ผู้ประกอบการx | yเป็นอย่างพอเพียงที่แตกต่างกันทางสายตา (ในแบบอักษรพิมพ์ดีด) จากx || yแต่ฉันพบว่า!ในเช่นง่ายต่อการพลาดกว่าif (!f(xyz) && ... if (not f(xyz) && ...
Tony Delroy

@Tony D เมื่อคุณใส่ช่องว่างรอบตัวดำเนินการนั่นคือการประชุมส่วนตัวของคุณและไม่ชัดเจนสำหรับผู้อ่าน แต่การใช้คำภาษาธรรมชาติชอบand, orและnotในการแสดงออกบูลจริงช่วยเพิ่มความสามารถในการอ่านรวมทั้งจะเน้นความแตกต่างในการผสมบิต ดังนั้น IMHO เราควรพิจารณาเปลี่ยนนิสัยเดิม ๆ ที่เรารักให้ดีขึ้น ...
Ichthyo

@DanNissenbaum ฉันพบตัวเลือกนี้ภายใต้ชื่อC / C ++> ภาษา> ปิดการใช้งานส่วนขยายภาษาดังนั้นจึงค่อนข้างปลอดภัยที่จะคาดหวังผลข้างเคียง;)
Wolf

6
คุณรู้หรือไม่ว่ามีข้อบกพร่องของ Python กี่ตัวที่ถูกนำมาใช้เนื่องจากคำพูดandและorอคติของผู้คนที่คิดว่ามันควรจะทำงานอย่างไร? เช่นif (a == b or c)แทนที่จะif (a == b || a == c)- สิ่งนี้จะปรากฏขึ้นเกือบทุกวันที่ StackOverflow สัญลักษณ์นามธรรมที่ไม่เชื่อมต่อกับภาษาอังกฤษจะช่วยลดข้อผิดพลาดเหล่านี้
Mark Ransom

10

ใน C ++ เป็นคำหลักที่แท้จริง ใน C คือมาโครที่กำหนดไว้ใน<iso646.h>. ดูhttp://web.archive.org/web/20120123073126/http://www.dinkumware.com/manuals/?manual=compleat&page=iso646.html


6
ในทางเทคนิคเป็นโทเค็นสำรองไม่ใช่คำหลัก :)
GManNickG

2
@GMan: +1 การโทรที่ดีแม้ว่าหน้า Dinkumware จะเรียกพวกเขาว่าคีย์เวิร์ดดังนั้นฉันคิดว่าพวกเขาไม่สนใจเกี่ยวกับความแตกต่างมากเกินไป
Chris Jester-Young

ลิงค์อัพเดท: f3.tiera.ru/1/addesio/computer-science/C&C++/…
kevinarpe

ดังนั้น MSVC จึงสนับสนุนพวกเขานอกกรอบใน C ++ แต่ไม่ใช่ใน C หรือไม่?
rwst

1
@rwst ฉันไม่สามารถแสดงความคิดเห็นเกี่ยวกับ MSVC โดยเฉพาะ แต่ถ้าใช้มาตรฐาน C ++ และ C อย่างซื่อสัตย์ก็จะเป็นเช่นนั้น ดูเพิ่มเติม: stackoverflow.com/questions/2376448/…
Chris Jester-Young

2

andและ&&ทำงานเหมือนกันใน C ++ ตัวดำเนินการandและorเป็น C ++ ที่ถูกต้องและเป็นส่วนหนึ่งของมาตรฐานภาษา

การทำอย่างละเอียดในคำตอบอื่น ๆ ด้วยตัวอย่างคอนกรีตมีเหตุผลที่นอกเหนือจากเพียงแค่ "การอ่าน" เพื่อต้องการอีกกว่าand &&การสะกด "และ" อย่างชัดเจนเมื่อตรรกะและเป็นสิ่งที่คุณหมายถึงจะช่วยขจัดความเป็นไปได้ของข้อบกพร่องที่ละเอียดอ่อน

พิจารณาสิ่งนี้:

int x = 3;
int y = 4;

// Explicitly use "and"
if (x and y) {
    cout << "and: x and y are both non-zero values" << endl;
}

// Using "&&"
if (x && y) {
    cout << "&&: x and y are both non-zero values" << endl;
}

// Oops! I meant to type "&&"!
if (x & y) {
    cout << "&: x and y are both non-zero values" << endl;
}
else {
    cout << "How did I get here?" << endl;
}

if-statement ทั้งสามจะคอมไพล์ แต่อันสุดท้ายหมายถึงสิ่งที่แตกต่างอย่างสิ้นเชิงและไม่ได้ตั้งใจ!

หากคุณใช้เสมอandเมื่อคุณหมายถึงตรรกะ AND คุณจะไม่สามารถพิมพ์ "&" โดยบังเอิญเพียงคำเดียวและทำให้โค้ดของคุณคอมไพล์สำเร็จและทำงานด้วยผลลัพธ์ที่ลึกลับ

การออกกำลังกายที่ดีอีกวิธีหนึ่ง: ลองทิ้งลักษณะของ "และ" ไว้โดยบังเอิญแล้วดูว่าเกิดอะไรขึ้น ;)


1
นี่ไม่ใช่คำตอบสำหรับคำถามจริงๆ เพียงแค่คุณระบุสิ่งที่คุณรู้สึกว่าชัดเจนมากขึ้น OP ถามเกี่ยวกับวิธีการทำงานของเวอร์ชันที่เขียนไม่ใช่แบบไหนดี และมีคนอื่นมาแล้วจุดเดียวกับที่คุณพยายามจะ
Nicol Bolas

ไม่ใช่ว่ามันจะให้ข้อมูลที่เป็นประโยชน์มากกว่านี้ แต่ฉันจะเพิ่มคำตอบ" andและ&&เหมือนกันตามหน้าที่" ... และถ้าคุณอ่านคำตอบของฉันคุณจะเห็นว่าฉันบอกว่ามันไม่เกี่ยวกับความชัดเจน;)
tjwrona1992
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.