0Pricing
Swift Academy · บทเรียน

any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต

ใช้ any P เพื่อจัดเก็บหรือส่งต่อชนิดที่สอดคล้องกับโพรโทคอลแต่มีชนิดหลากหลายไว้เบื้องหลังโพรโทคอล ทำความเข้าใจการเรียกแบบพลวัต การห่อค่า และข้อจำกัดของข้อกำหนด associated types / Self

any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต เป็นบทเรียน Swift Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 2 จากทั้งหมด 3 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน Swift Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส Swift Academy มีบทเรียนทั้งหมด 3 บทเรียน

ชนิดเอ็กซิสเทนเชียลคืออะไร

ชนิดเอ็กซิสเทนเชียล (any P) เก็บค่า ใด ๆ ที่สอดคล้องกับ P ชนิดเหล่านี้ช่วยให้จัดเก็บข้อมูลต่างชนิดร่วมกันและเรียกใช้แบบไดนามิกได้ แต่ก็มีข้อจำกัดบางประการ

  • เหมาะอย่างยิ่งสำหรับคอลเลกชันต่างชนิด
  • เรียกใช้แบบไดนามิกผ่านตารางตัวแทนการปฏิบัติตามโปรโตคอล
  • มีข้อจำกัดกับชนิดที่เกี่ยวข้องและการอ้างอิงตัวเอง

คอลเลกชันต่างชนิด

ค่ารูปร่างแบบต่างชนิดช่วยให้คุณจัดเก็บค่าที่สอดคล้องกับโปรโตคอล แตกต่างกันไว้ร่วมกัน และเรียกใช้เมธอดของโปรโตคอลผ่านการเรียกใช้แบบไดนามิกได้

protocol Shape { func area() -> Double }

struct Circle: Shape { let r: Double; func area() -> Double { .pi * r * r } }
struct Square: Shape { let s: Double; func area() -> Double { s * s } }

// Heterogeneous array using ANY Shape
let shapes: [any Shape] = [Circle(r: 1), Square(s: 2), Circle(r: 0.5)]
let total = shapes.reduce(0) { $0 + $1.area() }   // dynamic dispatch
print(String(format: "%.2f", total))

ขอบเขตของส่วนติดต่อ

ชนิดเอ็กซิสเทนเชียลเปิดเผยเฉพาะส่วนติดต่อของโปรโตคอลเท่านั้น เมธอดที่มีเฉพาะในชนิดรูปธรรมต้องใช้การแปลงชนิดลง (ซึ่งเป็นทางเลือกและตรวจสอบขณะทำงาน)

extension Circle { func diameter() -> Double { 2 * r } }

let mixed: [any Shape] = [Circle(r: 1), Square(s: 3)]
print(mixed[0].area())            // OK: in protocol
// print(mixed[0].diameter())     // ❌ Not visible via any Shape (commented)
// You'd need a type check / downcast:
if let c = mixed[0] as? Circle { print(c.diameter()) }

ข้อควรระวังเกี่ยวกับชนิดที่เกี่ยวข้อง

ชนิดเอ็กซิสเทนเชียลไม่สามารถพกชนิดที่เกี่ยวข้องที่ไม่ทราบชนิด หรือข้อกำหนดที่อ้างอิงตัวเองได้โดยตรง ให้ใช้การลบชนิด หรือกำหนดชนิดที่เกี่ยวข้องผ่านตัวห่อหุ้ม

// Protocols with associated types/Self constraints can be hard to use as existentials.
protocol Parser {
    associatedtype Output
    func parse(_ s: String) -> Output
}

// let p: any Parser = ...     // ❌ Not directly usable: Output is unknown
// Workarounds: type erasure or constrain Output to a specific type in wrappers.

การเลือกรูปแบบพารามิเตอร์

ชนิดเอ็กซิสเทนเชียล: ต่างชนิดและยืดหยุ่น เจเนอริก: ชนิดเดียวกันและเร็วกว่า/ตรวจสอบขณะคอมไพล์ เลือกให้เหมาะกับความต้องการ

// Existential: accepts any mix of Shapes (dynamic dispatch)
func totalAreaExistential(_ xs: [any Shape]) -> Double {
    xs.reduce(0) { $0 + $1.area() }
}

// Generic (homogeneous): static dispatch; one concrete Shape type per call
func totalAreaGeneric<S: Sequence, T: Shape>(_ xs: S) -> Double
where S.Element == T {
    xs.reduce(0) { $0 + $1.area() }
}

print(totalAreaExistential([Circle(r:1), Square(s:2)]))  // mixed OK
print(totalAreaGeneric([Circle(r:1), Circle(r:2)]))      // homogeneous only
// totalAreaGeneric([Circle(r:1), Square(s:2)])          // ❌ different types

เมื่อใดควรใช้ any P

แนวทาง:

  • ใช้ any P สำหรับการจัดเก็บข้อมูลต่างชนิดและพหุรูปแบบขณะทำงาน
  • เลือกใช้เจเนอริกเพื่อประสิทธิภาพและการรับประกันแบบคงที่เมื่อองค์ประกอบเป็นชนิดเดียวกัน
  • หลีกเลี่ยงชนิดเอ็กซิสเทนเชียลสำหรับโปรโตคอลที่มีชนิดที่เกี่ยวข้องหรือการอ้างอิงตัวเอง เว้นแต่จะใช้การลบชนิดหรือตัวห่อหุ้ม

ประโยชน์ของชนิดเอ็กซิสเทนเชียล

ตรวจสอบสั้น ๆ: any P ช่วยให้ทำอะไรได้บ้าง

ทบทวน

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

คำถามที่พบบ่อย

บทเรียน “any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต” ฟรีหรือไม่

ใช่ — ข้อความเต็มของ “any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส Swift Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส Swift Academy มีบทเรียนทั้งหมด 3 บทเรียน

คุณจะเรียนรู้อะไรในบทเรียน “any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต”

ใช้ any P เพื่อจัดเก็บหรือส่งต่อชนิดที่สอดคล้องกับโพรโทคอลแต่มีชนิดหลากหลายไว้เบื้องหลังโพรโทคอล ทำความเข้าใจการเรียกแบบพลวัต การห่อค่า และข้อจำกัดของข้อกำหนด associated types / Self คุณปฏิบัติ Swift Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน

คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน Swift Academy หรือไม่

ไม่จำเป็นต้องมีประสบการณ์มาก่อน Swift Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 2 จากทั้งหมด 3 บทเรียน

บทเรียน “any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต” ใช้เวลานานแค่ไหน

บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย

ฉันเขียนและรันโค้ดในบทเรียน Swift Academy นี้ได้ไหม

ได้ บทเรียน Swift Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ

บทเรียนทั้งหมดในหลักสูตรนี้

  1. some P (ชนิดผลลัพธ์แบบไม่เปิดเผย): ซ่อนชนิดรูปธรรม
  2. any P (ชนิดอัตถิภาวะ): ข้อแลกเปลี่ยนและการเรียกแบบพลวัต
  3. การเลือกระหว่าง some, any และเจเนอิกส์
← กลับไปที่ Swift Academy