JavaScript: อาร์เรย์ว่าง [] ประเมินเป็นจริงในโครงสร้างเงื่อนไข ทำไมถึงเป็นแบบนี้?


101

ฉันพบข้อบกพร่องมากมายในโค้ดของฉันเพราะฉันคาดหวังนิพจน์นี้:

Boolean([]); เพื่อประเมินเป็นเท็จ

แต่นี่ไม่ใช่กรณีที่ประเมินว่าเป็นจริง

ดังนั้นฟังก์ชันที่อาจส่งกลับ[]เช่นนี้:

// Where myCollection possibly returned [ obj1, obj2, obj3] or []
if(myCollection)
{
  // ...

}else
{
  // ...
}

ไม่ได้ทำสิ่งที่คาดหวัง

ฉันเข้าใจผิดในการสมมติว่า[]อาร์เรย์ว่างเปล่า?

นอกจากนี้พฤติกรรมนี้สอดคล้องกันในทุกเบราว์เซอร์หรือไม่ หรือมี gotchas อยู่ที่นั่นด้วย? ฉันสังเกตพฤติกรรมนี้ใน Goolgle Chrome โดยวิธีการ


5
อาร์เรย์เป็นวัตถุวัตถุมีความจริง แค่ขอ array.length ถ้าไม่ใช่ศูนย์มันจะเป็นจริง เมื่อคุณแปลงเป็นบูลีนอย่างชัดเจนอาร์เรย์จะเปลี่ยนเป็นสตริงว่างก่อนจากนั้นสตริงว่างจะเปลี่ยนเป็นเท็จ
dandavis

1
ทำไมคุณไม่ใช้myCollection.length > 0?
Steve

1
@ Steve - ว่าจะไม่ทำงานหากmyCollectionเกิดขึ้นจะเป็นหรือnull คุณจำเป็นต้องใช้undefined if(myCollection && myCollection.length > 0)
Ted Hopp

@TedHopp - แน่นอน ... ฉันแค่ชี้ให้เห็นว่าmyCollection.length > 0มีค่าบูลีนที่ทำในสิ่งที่ OP ขอ ... เขายังต้องทำงานจากที่นั่น
Steve

คำตอบ:


120

จากhttp://www.sitepoint.com/javascript-truthy-falsy/

ค่าต่อไปนี้มักเป็นเท็จเสมอ:

  • เท็จ
  • 0 (ศูนย์)
  • "" (สตริงว่าง)
  • โมฆะ
  • ไม่ได้กำหนด
  • NaN (ค่าตัวเลขพิเศษหมายถึงไม่ใช่ตัวเลข!)

ค่าอื่น ๆ ทั้งหมดเป็นค่าความจริงรวมถึง "0" (ศูนย์ในเครื่องหมายคำพูด) "เท็จ" (เท็จในเครื่องหมายคำพูด) ฟังก์ชันว่างอาร์เรย์ว่างและวัตถุว่าง

เกี่ยวกับสาเหตุที่เป็นเช่นนั้นฉันสงสัยว่าเป็นเพราะอาร์เรย์ JavaScript เป็นเพียงวัตถุประเภทหนึ่ง Array.isArray()อาร์เรย์รักษาเป็นพิเศษจะต้องมีค่าใช้จ่ายเพิ่มเติมในการทดสอบ นอกจากนี้อาจทำให้เกิดความสับสนหากอาร์เรย์ที่แท้จริงทำงานแตกต่างจากอ็อบเจ็กต์อื่น ๆ ที่คล้ายอาร์เรย์ในบริบทนี้ในขณะที่การทำให้อ็อบเจ็กต์ที่มีลักษณะคล้ายอาร์เรย์ทั้งหมดทำงานเหมือนกันจะมีราคาแพงกว่า


28
หากคุณทดสอบการแสดงออกมันประเมิน[] == false true
m.rufca


มีตารางจำนวนหนึ่งที่แสดงสถานการณ์ที่ไม่คาดคิดโดยใช้ตัว==เปรียบเทียบในลิงก์ที่คุณโพสต์ ฉันแสดงความคิดเห็นเพียงเพื่อระมัดระวังเมื่อคาดหวังการประเมินผลจริงหรือเท็จ
m.rufca

4
สิ่งนี้ไม่ได้ตอบคำถามจริงๆว่าทำไม ทำไมอาร์เรย์ว่างเปล่าจึงเป็นจริงเมื่อสตริงว่างเป็นเท็จ เนื่องจากการตัดสินใจออกแบบโดยเจตนาทำให้รู้สึกแย่มาก
Esa Lindqvist

1
อาจเป็นเพราะสิ่งเหล่านี้จำเป็นต้องทำหน้าที่เหมือนวัตถุดั้งเดิม แต่ Javascript ไม่มีอาร์เรย์ดั้งเดิม
Barmar

28

คุณควรตรวจสอบ.lengthอาร์เรย์นั้นเพื่อดูว่ามีองค์ประกอบหรือไม่

if (myCollection) // always true
if (myCollection.length) // always true when array has elements
if (myCollection.length === 0) // same as is_empty(myCollection)

@marczellm ความคิดเห็นจากสตีฟที่ล้าสมัยเขาแจ้ง DevIshOne เกี่ยวกับสภาพที่ขาดหายไป"เมื่ออาร์เรย์มีองค์ประกอบ"ซึ่งได้รับการแก้ไขด้วยเหตุนี้ในการแก้ไข
mucaho
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.