ฉันมีประสบการณ์ในการเขียนเครื่องมือขนาดเล็กใน Haskell และฉันพบว่ามันใช้งานง่ายมากโดยเฉพาะการเขียนตัวกรอง (โดยใช้interact
) ที่ประมวลผลอินพุตมาตรฐานและไพพ์ไปยังเอาต์พุตมาตรฐาน
เมื่อเร็ว ๆ นี้ฉันพยายามใช้ตัวกรองดังกล่าวกับไฟล์ที่มีขนาดใหญ่กว่าปกติประมาณ 10 เท่าและฉันพบStack space overflow
ข้อผิดพลาด
หลังจากอ่านบางส่วน (เช่นที่นี่และที่นี่ ) ฉันได้ระบุแนวทางสองข้อเพื่อประหยัดพื้นที่สแต็ก (Haskellers ที่มีประสบการณ์โปรดแก้ไขให้ฉันถ้าฉันเขียนสิ่งที่ไม่ถูกต้อง):
- หลีกเลี่ยงการเรียกฟังก์ชั่นแบบเรียกซ้ำที่ไม่ใช่แบบเรียกซ้ำ (ใช้ได้กับทุกภาษาที่ใช้งานได้ซึ่งรองรับการปรับให้เหมาะสมแบบหางเรียก)
- แนะนำ
seq
ให้บังคับให้มีการประเมินผลก่อนของนิพจน์ย่อยเพื่อให้นิพจน์ไม่ใหญ่เกินไปก่อนที่จะถูกลดขนาดลง (นี่เป็นลักษณะเฉพาะของ Haskell หรืออย่างน้อยก็สำหรับภาษาที่ใช้การประเมินแบบขี้เกียจ)
หลังจากแนะนำการseq
โทรห้าหรือหกครั้งในรหัสของฉันเครื่องมือของฉันจะทำงานได้อย่างราบรื่นอีกครั้ง (เช่นเดียวกับข้อมูลขนาดใหญ่) อย่างไรก็ตามฉันพบว่ารหัสต้นฉบับอ่านง่ายขึ้นอีกเล็กน้อย
เนื่องจากฉันไม่ใช่โปรแกรมเมอร์ Haskell ที่มีประสบการณ์ฉันต้องการถามว่าการแนะนำseq
ด้วยวิธีนี้เป็นวิธีปฏิบัติทั่วไปหรือไม่และบ่อยครั้งที่บุคคลทั่วไปจะเห็นseq
ในรหัสการผลิต Haskell หรือมีเทคนิคใดบ้างที่อนุญาตให้หลีกเลี่ยงการใช้seq
บ่อยเกินไปและยังคงใช้พื้นที่สแต็กน้อย?