javascript - การประกาศชนิดทำงานกับ object literal แต่ไม่ทำงานกับการใช้งานคลาส
ฉันต้องการชนิดข้อมูลเพื่อแทนค่าพิกัด ชนิดข้อมูลที่ฉันนำไปใช้กับอินเทอร์เฟซนั้นใช้ได้กับอ็อบเจ็กต์แต่ไม่สามารถใช้กับคลาสได้
type ICoord = [number, number]
type MyInterface = {
a: ICoord
}
var obj: MyInterface = { // works
a: [0, 0]
}
class C implements MyInterface { // gets below compilation error
a = [0, 0]
}
คุณสมบัติ 'a' ในประเภท 'C' ไม่สามารถกำหนดค่าให้กับคุณสมบัติเดียวกันในประเภทฐาน 'MyInterface' ได้ ประเภท 'number[]' ขาดคุณสมบัติต่อไปนี้จากประเภท '[number, number]': 0, 1
ทำไมฉันถึงไม่สามารถกำหนดค่า [0, 0] ให้กับ a ได้?
[สนามเด็กเล่น TypeScript]
คำตอบ #1
ประเภทของ a ถูกสันนิษฐานว่าเป็น number[] ซึ่งไม่สามารถกำหนดค่าให้กับทูเพิล [number, number] ได้ การกำหนดประเภทแบบชัดเจนเป็น ICoord สำหรับ a ดูเหมือนว่าจะใช้ได้:
type ICoord = [number, number];
type MyInterface = {
a: ICoord;
}
class C implements MyInterface {
a: ICoord = [0, 0];
}
สนามเด็กเล่น TypeScript
คำตอบ #2
นี่เกี่ยวข้องกับการพิมพ์ตามบริบท
Typescript ใช้ประเภทที่คาดหวังของนิพจน์ (MyInterface ในกรณีนี้) เพื่อทำการอนุมานที่ดีกว่าเกี่ยวกับออบเจกต์ลิเทอรัล (รวมถึงพารามิเตอร์ฟังก์ชันด้วย) นี่คือเหตุผลว่าทำไมการกำหนดค่าออบเจกต์ลิเทอรัลจึงทำงานได้ดี และแอเรย์ลิเทอรัลถูกพิมพ์เป็นประเภททูเพิล
สำหรับคลาส สิ่งต่าง ๆ จะแตกต่างออกไปเล็กน้อย ส่วน implements ใช้เพื่อตรวจสอบว่าคลาสนั้นทำการใช้งานอินเทอร์เฟซอย่างถูกต้องหลังจากที่คลาสถูกพิมพ์ชนิดอย่างอิสระแล้ว คำสำคัญ implements จะไม่สร้างการพิมพ์บริบทใด ๆ สำหรับสมาชิกของคลาส นี่ก็เป็นสาเหตุที่คุณต้องระบุชนิดของพารามิเตอร์ฟังก์ชันแม้ว่าจะสามารถเดาได้จากอินเทอร์เฟซหรือคลาสพื้นฐาน
