รีแฟคเตอร์อีกครั้ง
เมื่อไลบรารีตัวช่วยเติบโตขึ้น การดูอย่างรวดเร็วจะติดตามได้ยากขึ้น ปรับโครงสร้างใหม่อีกครั้งเพื่อให้แต่ละฟังก์ชันมีขนาดเล็กและมีวัตถุประสงค์เดียว
ทำลายความซับซ้อน
เพื่อให้ติดตามและบำรุงรักษาฟังก์ชันได้ง่ายขึ้น ให้แบ่งฟังก์ชันออกเป็นฟังก์ชันที่เน้นและมีขนาดเล็กลง เริ่มต้นด้วยการแยกการตรวจสอบความถูกต้องออกจากการกำหนดเส้นทางข้อความ
สร้างฟังก์ชันการตรวจสอบความถูกต้อง
เราสามารถใช้ส่วนหนึ่งของฟังก์ชันที่ตรวจสอบอาร์กิวเมนต์ message และ output และย้ายไปยังฟังก์ชันที่แยกจากกัน ด้วยวิธีนี้ ฟังก์ชันหลัก send-message ไม่จำเป็นต้องกังวลเกี่ยวกับการตรวจสอบความถูกต้อง ทำให้ง่ายต่อการติดตาม
(define (validate-message message output)
;; Check if the message is a non-empty string
(if (or (not (string? message)) (string=? message ""))
(error "Message must be a non-empty string"))
;; Check if the output is one of the expected destinations
(if (not (member output '(gui error-console terminal)))
(error "Invalid output destination: " output)))ลดความซับซ้อนในการส่งข้อความ
เมื่อการตรวจสอบถูกย้ายไปยังฟังก์ชันที่แยกจากกัน ฟังก์ชัน send-message จึงสามารถมุ่งเน้นไปที่การส่งข้อความเท่านั้น มันจะง่ายกว่ามากเนื่องจากจะจัดการเฉพาะงานเฉพาะในการส่งข้อความไปยังปลายทางที่ถูกต้องเท่านั้น
(define (send-message message output)
;; Call the validation function before proceeding
(validate-message message output)
(cond
;; Send to the Error Console
((eq? output 'error-console)
(lumi-message-set-handler 2)
(lumi-message message))
;; Send to the GUI dialog box
((eq? output 'gui)
(lumi-message-set-handler 0)
(lumi-message message))
;; Send to the terminal window
((eq? output 'terminal)
(display message)))
;; Restore the default message handler to the Error Console
(lumi-message-set-handler 2))พังทลายเพิ่มเติม: แยกตัวจัดการเอาต์พุตแต่ละตัว
เอาต์พุตข้อความแต่ละประเภท (GUI, Error Console, Terminal) สามารถย้ายไปยังฟังก์ชันของตัวเองได้ ซึ่งช่วยให้ทดสอบ แก้ไข และขยายศักยภาพได้ง่ายขึ้นในอนาคต
(define (send-to-gui message)
(lumi-message-set-handler 0)
(lumi-message message))
(define (send-to-error-console message)
(lumi-message-set-handler 2)
(lumi-message message))
(define (send-to-terminal message)
(display message))
(define (send-message message output)
;; Send to the appropriate output
(cond
((eq? output 'error-console) (send-to-error-console message))
((eq? output 'gui) (send-to-gui message))
((eq? output 'terminal) (send-to-terminal message)))
;; Restore the default message handler to the Error Console
(lumi-message-set-handler 2))ใช้การตรวจสอบซ้ำในแต่ละฟังก์ชันส่ง
เนื่องจากการตรวจสอบเป็นส่วนสำคัญในการตรวจสอบให้แน่ใจว่าทั้งข้อความและเอาต์พุตถูกต้อง จึงสมเหตุสมผลที่ฟังก์ชัน send-* แต่ละตัวจะดำเนินการตรวจสอบความถูกต้องของตัวเอง สิ่งนี้ทำให้แน่ใจได้ว่าไม่ว่าจะเรียกเอาต์พุตใด เราจะตรวจสอบอินพุตก่อนเสมอ
(define (send-to-gui message)
;; Validate the message before proceeding
(validate-message message 'gui)
(lumi-message-set-handler 0)
(lumi-message message))
(define (send-to-error-console message)
;; Validate the message before proceeding
(validate-message message 'error-console)
(lumi-message-set-handler 2)
(lumi-message message))
(define (send-to-terminal message)
;; Validate the message before proceeding
(validate-message message 'terminal)
(display message))ดูว่าเราได้ลบการตรวจสอบความถูกต้องออกจากฟังก์ชันส่งข้อความแล้ว และเปลี่ยนความรับผิดชอบไปที่ฟังก์ชันเอาต์พุตแต่ละรายการ การเปลี่ยนแปลงนี้ทำให้มั่นใจได้ว่าแต่ละปลายทาง (GUI, Error Console, Terminal) จะจัดการการตรวจสอบของตัวเอง ปรับปรุงฟังก์ชันส่งข้อความ และรักษาตรรกะการตรวจสอบให้ใกล้กับจุดที่จำเป็นมากขึ้น
วิธีการนี้สามารถลดความซับซ้อนของฟังก์ชันส่งข้อความ ทำให้เป็น dispatcher ในขณะที่ทำให้มั่นใจได้ว่าแต่ละฟังก์ชัน send-to-* จะตรวจสอบข้อความอย่างถูกต้องก่อนประมวลผล
ด้วยการย้ายการตรวจสอบไปยังฟังก์ชัน send-to-* แต่ละฟังก์ชัน เราได้ทำให้สามารถนำมาใช้ใหม่เป็นฟังก์ชันแบบสแตนด์อโลนได้ ซึ่งหมายความว่าเราสามารถเรียกใช้ฟังก์ชัน send-to-gui, send-to-error-console หรือ send-to-terminal ใดๆ ได้โดยตรง โดยไม่ต้องอาศัยฟังก์ชัน send-message Dispatcher แต่ละฟังก์ชันเหล่านี้จัดการตรรกะของตัวเองได้อย่างสมบูรณ์แล้ว และสามารถใช้อย่างอิสระในส่วนอื่นๆ ของโค้ดหรือในปลั๊กอินอื่นๆ ทำให้โค้ดของคุณเป็นแบบโมดูลาร์และยืดหยุ่นมากขึ้น
ประโยชน์ของการปรับโครงสร้างใหม่
- การแยกข้อกังวลอย่างชัดเจน: ตอนนี้แต่ละฟังก์ชันจะจัดการความรับผิดชอบเพียงข้อเดียว ทำให้โค้ดเข้าใจได้ง่ายขึ้น
- ความสามารถในการขยาย: การเพิ่มประเภทเอาต์พุตใหม่นั้นตรงไปตรงมา คุณเพียงกำหนดฟังก์ชันใหม่ เช่น
send-to-fileหรือsend-to-loggerจากนั้นเพิ่มตัวพิมพ์ลงในคำสั่งcond - การนำกลับมาใช้ใหม่ได้: แต่ละฟังก์ชันการจัดการเอาต์พุตเหล่านี้สามารถนำมาใช้ซ้ำที่อื่นในโปรเจ็กต์ของคุณ หรือใช้ร่วมกันระหว่างปลั๊กอินหลายตัวได้
- ความสม่ำเสมอ: การนำฟังก์ชันการตรวจสอบความถูกต้องกลับมาใช้ใหม่ในแต่ละฟังก์ชัน
send-to-*จะทำให้คุณมั่นใจได้ว่าเอาต์พุตทั้งหมดได้รับการตรวจสอบอย่างถูกต้อง ซึ่งจะทำให้โค้ดมีประสิทธิภาพมากขึ้น
เวอร์ชันไลบรารีที่ปรับโครงสร้างใหม่:
;; Purpose: Sends a message to the GUI dialog box
(define (send-to-gui message)
;; Validate the message before proceeding
(validate-message message 'gui)
(lumi-message-set-handler 0)
(lumi-message message))
;; Purpose: Sends a message to the Error Console
(define (send-to-error-console message)
;; Validate the message before proceeding
(validate-message message 'error-console)
(lumi-message-set-handler 2)
(lumi-message message))
;; Purpose: Sends a message to the terminal window
(define (send-to-terminal message)
;; Validate the message before proceeding
(validate-message message 'terminal)
(display message))
;; Purpose: Dispatches a message to the appropriate output destination
(define (send-message message output)
(cond
((eq? output 'error-console) (send-to-error-console message))
((eq? output 'gui) (send-to-gui message))
((eq? output 'terminal) (send-to-terminal message)))
;; Restore the default message handler to the Error Console
(lumi-message-set-handler 2))
;; Purpose: Validates that the message is a non-empty string and the output is valid
(define (validate-message message output)
;; Check if the message is a non-empty string
(if (or (not (string? message)) (string=? message ""))
(error "Message must be a non-empty string"))
;; Check if the output is one of the expected destinations
(if (not (member output '(gui error-console terminal)))
(error "Invalid output destination: " output)))นั่นคือทั้งหมดที่เราสามารถทำได้? เลขที่! ยังมีอะไรที่ต้องทำอีกมาก โปรดอ่านต่อ