เมื่อตะขอเป็นตัวเลือกการออกแบบที่ถูกต้อง


10

ฉันได้ทำงานกับแอพ Rails ขนาดใหญ่ซึ่งการใช้งานการเรียกกลับของ ActiveRecord นั้นอาละวาดและบาดใจ การบันทึกมักจะมีผลข้างเคียงที่ไม่คาดคิดและมันเป็นความท้าทายที่จะให้เหตุผลเกี่ยวกับระบบ

ในเวลาเดียวกันฉันเคยเห็น hooks ใช้เพื่อให้เกิดผลดีในฐานะส่วนหนึ่งของการสืบทอด (เช่นคลาสแม่ที่ใช้แม่แบบวิธีการเพื่อให้คลาสย่อยเพิ่มพฤติกรรมพิเศษโดยไม่จำเป็นต้องรู้เกี่ยวกับ internals ของผู้ปกครอง) และปลั๊กอิน (เช่นโหมด emacs ที่เรียกใช้ hook เมื่อเปิดใช้งานช่วยให้ผู้ใช้สามารถเพิ่มพฤติกรรมที่กำหนดเองในโหมดนั้น)

ฉันรู้ว่าแอพพลิเคชั่น Rails และ Lisp เป็นระบบที่แตกต่างกันอย่างมาก แต่ฉันอยากรู้ว่ามีเกณฑ์อะไรที่คนรู้จักกันดีเมื่อตัดสินใจว่า hooks เป็นตัวเลือกที่เหมาะสมสำหรับปัญหาที่พวกเขากำลังเผชิญหรือไม่

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

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

คำตอบ:


5

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

คุณสามารถทำได้โดยการออกอากาศที่ไม่ระบุชื่อ (เช่นเหตุการณ์หรือการเรียกกลับที่ไม่ระบุชื่อ) หรือโดยใช้ abstractions ที่พิมพ์ (เช่นอินเทอร์เฟซหรือคลาสแม่)

คุณควรใช้การออกอากาศแบบไม่ระบุชื่อเมื่อ:

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

คุณควรใช้นามธรรมที่พิมพ์เมื่อ:

  • การเรียกขอ hook นั้นจำเป็น
  • วัตถุที่เรียกต้องระบุตัวรับของ hook
  • ลำดับของการดำเนินการของผู้รับที่เกี่ยวข้องกับวัตถุของคุณ

ตัวอย่างของ hook การออกอากาศคือ KeyPressedEvent ชั้นเรียนที่จัดกิจกรรมไม่สนใจว่าใครจะได้รับและเผยแพร่สถานะแป้นพิมพ์ให้กับทุกคนที่สมัครรับข้อมูลกิจกรรม ลำดับการดำเนินการของผู้รับไม่มีผลกระทบกับสถานะวัตถุของคลาสที่เริ่มเหตุการณ์

ตัวอย่างของ hook abstraction ที่พิมพ์เป็นวิธีแม่แบบที่คุณพูดถึง ในกรณีนี้คลาสพาเรนต์ต้องการการใช้งานสำหรับวิธีเทมเพลตมันรู้ว่าผู้รับจะเป็น childs ของมันและมันมีลำดับการดำเนินการที่เฉพาะเจาะจงสำหรับวิธีการแม่แบบตามที่กำหนดโดยระดับผู้ปกครอง


7

ภาษาส่วนใหญ่และแพลตฟอร์มส่วนใหญ่ใช้ hooking แม้ว่าจะแต่งตัวเป็นอย่างอื่น เมื่อใดก็ตามที่คุณได้ยินคำว่า "เหตุการณ์" "ข้อความ" "ทริกเกอร์" "สัญญาณ" หรือข้อกำหนดอื่น ๆ ของลักษณะนั้นคุณอาจกำลังติดต่อกับตะขอแม้ว่าจะมีข้อยกเว้นกฎซึ่งอาจจะไม่ เรื่องสำหรับการสนทนานี้

คุณใช้พวกเขาเพราะแพลตฟอร์มให้พวกเขาหรืออาจต้องใช้พวกเขาด้วยเหตุผลด้านประสิทธิภาพ การใช้ hooks มักจะลดความซับซ้อนของรหัสช่วยในการบังคับใช้ข้อกำหนดทางธุรกิจและลดการใช้งาน CPU ยืดอายุแบตเตอรี่และฮาร์ดแวร์ คุณควรใช้มันทุกครั้งที่คุณต้องการประสิทธิภาพที่ดีที่สุดจากรหัสของคุณ

แม้แต่ประสบการณ์ที่บาดใจของคุณกับ Rails ก็ยังระบุถึงกรณีการใช้งานทั่วไปสำหรับ hooks: กฎเกณฑ์ทางธุรกิจจะต้องมีการบังคับใช้และ hooks มีการใช้อย่างแพร่หลายในการบังคับใช้กฎเกณฑ์ทางธุรกิจ น่าเสียดายที่ไม่ใช่กฎทุกข้อที่สมเหตุสมผลและอย่างที่คุณบอกได้มันทำให้ทุกอย่างยากขึ้นสำหรับนักพัฒนาเมื่อมันถูกสร้างขึ้นโดยพลการ แต่นั่นเป็นสาเหตุที่เอกสารของระบบมีความสำคัญเทียบเท่ากับรหัส

ตามกฎทั่วไปให้ใช้ hooks เพราะเป็นคุณสมบัติด้านประสิทธิภาพและจะทำให้โค้ดของคุณทำงานได้อย่างมีประสิทธิภาพมากกว่าทางเลือกอื่น (ซึ่งเรียกว่า "การสำรวจ" ซึ่งคุณจะรอในการวนรอบไม่ว่างเพื่อตรวจสอบเหตุการณ์) อย่างไรก็ตามตรวจสอบให้แน่ใจว่าคุณใช้เอกสารที่เหมาะสมและปรับปรุงให้ทันสมัยอยู่เสมอ ตะขอถูกใช้ในแทบทุกภาษาที่คุณจะพบและเป็นสิ่งสำคัญที่จะต้องรู้ว่าทำไมมันถึงมีอยู่


1

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

ถ้าไม่คุณควรไปกับส่วนที่ดีของโมดูลของคุณ เทมเพลต - วิธีการทำงานได้ดีกับฟังก์ชั่นที่มีการโอเวอร์โหลดคุณไม่จำเป็นต้องมีตรรกะแบบรันไทม์สำหรับสิ่งนี้ พิจารณาว่ามันจะบังคับใช้การแต่งงานกันแบบคับแคบเป็นภาพลวงตา: มีระดับการพึ่งพาระหว่างสิ่งที่คุณโทรหาโดยตรงหรือคุณขอความร่วมมือก็ต้องเติมเต็มสัญญา

โปรดทราบว่าบางคนอาจเรียกแม่แบบวิธีการที่มีฟังก์ชั่นโอเวอร์โหลด แต่แตกต่างจากข้างต้น: ที่นี่คุณมีการเชื่อมโยงแบบคงที่โดยมีความเสี่ยงต่ำกว่าในการเข้าสู่ฝันร้ายในการบำรุงรักษา

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