เทคนิคการเขียนโปรแกรมนี้เรียกว่าอะไร?


13

ฉันเจอเทคนิคการเขียนโปรแกรมนี้ในขณะที่ทำการเขียนโปรแกรมจับคู่ในการสัมภาษณ์และไม่พบชื่อของมันใน google

แนวคิดคือคุณเขียนนิพจน์ที่ใช้ตัวแปรก่อนแล้วจึงเขียนโค้ดที่คำนวณตัวแปรในภายหลัง

วิธีใช้โค้ดตัวอย่างที่นี่:

private bool ValidPolicyNumber(string policyNumber) 
{
    var hasExpectedPrefix = policyNumber.Substring(0,5) == "POLIC";
    var followedBy7Digits = Regex.IsMatch(policyNumber.Substring(6,7), "^[0-9]{7}$");
    var hasLengthOf12 = policyNumber.Length == 12;

    return hasExpectedPrefix && followedBy7Digits && hasLengthOf12;
}

เมื่อเขียนฟังก์ชั่นนี้โดยใช้เทคนิคที่ฉันพูดถึงคุณต้องเขียนบรรทัดสุดท้ายก่อนreturn hasExpectedPrefix && followedBy7Digits && hasLengthOf12;แล้วจึงเขียน 3 บรรทัดที่อยู่ข้างหน้า

เทคนิคที่ใกล้เคียงที่สุดที่ฉันสามารถหาได้คือ "การคิดอย่างปรารถนา" และมาจาก SICP แต่เกี่ยวข้องกับการเรียกฟังก์ชั่นที่คุณจะนำไปใช้ในภายหลังแทนที่จะใช้ตัวแปรที่คุณจะเริ่มต้นในภายหลัง


8
ฉันเชื่อว่านี่เป็นเพียงรูปแบบหนึ่งของการออกแบบจากบนลงล่าง
Vincent Savard

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

ฉันทำสิ่งนี้แล้ว คุณใช้รหัสเพื่อร่างแนวคิดโดยไม่ทำให้รายละเอียดมากเกินไปในตอนแรก หลังจากนั้น IDE ก็บ่นว่ามีบางอย่างที่ไม่มีอยู่คุณก็เลยทำให้มันเป็นจริง ช่วยเมื่อคุณมีการทดสอบที่จะล้มเหลวจนกว่าคุณจะได้รับการตกแต่ง
candied_orange

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

ฉันจะเรียกมันว่า "การเขียนเงื่อนไขที่ซับซ้อนอย่างมีเหตุผล"
Jimmy Breck-McKye

คำตอบ:


13

มันเป็นเพียงการเปลี่ยนแปลงขององค์ประกอบการทำงาน

พยาน:

private bool ValidPolicyNumber(string policyNumber) 
{
    return hasExpectedPrefix(policyNumber) 
        && followedBy7Digits(policyNumber) 
        && hasLengthOf12(policyNumber);
}

private bool hasExpectedPrefix(string policyNumber)
{
    return policyNumber.Substring(0,5) == "POLIC";
}

private bool followedBy7Digits
{
    return Regex.IsMatch(policyNumber.Substring(6,7), "^[0-9]{7}$");
}

private bool hasLengthOf12
{
    return policyNumber.Length == 12;
}

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


9

นี่อาจเป็นข้อเสนอแนะจาก Clean Code (หนังสือ) เพื่อใช้เมื่อ Function Decomposition (ดังที่ Robert อธิบายไว้) ไม่สามารถใช้งานได้เนื่องจากฟังก์ชั่นที่ไม่ได้นำมาใช้ซ้ำได้ด้วยตนเอง

อย่างไรก็ตามหากคุณต้องการได้รับข้อมูลเชิงเทคนิคเกี่ยวกับเรื่องนี้รูปแบบการนำไปปฏิบัติของหนังสือโดย Kent Beck ตั้งชื่อเทคนิคนี้ว่าExplaining Local Variables (focus mine):

ตัวแปรท้องถิ่น

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

มีบทบาททั่วไปจำนวนหนึ่งสำหรับตัวแปรท้องถิ่น:

  • นักสะสม: ตัวแปรที่รวบรวมข้อมูลเพื่อใช้ในภายหลัง บ่อยครั้งที่เนื้อหาของนักสะสมจะถูกส่งกลับเป็นค่าของฟังก์ชั่น เมื่อนักสะสมจะถูกส่งกลับให้ตั้งชื่อผลลัพธ์หรือผลลัพธ์

  • Count: นักสะสมพิเศษที่รวบรวมจำนวนวัตถุอื่น ๆ

  • การอธิบาย: หากคุณมีนิพจน์ที่ซับซ้อนการกำหนดบิตของนิพจน์ให้กับตัวแปรโลคัลสามารถช่วยผู้อ่านนำทางความซับซ้อน:

    int top = ... ;

    int left = ... ;

    int height = ... ;

    ด้านล่าง int = ... ;

    ส่งคืนสี่เหลี่ยมผืนผ้าใหม่ (บน, ซ้าย, ความสูง, ความกว้าง);

    ในขณะที่ไม่จำเป็นต้องใช้คอมพิวเตอร์การอธิบายตัวแปรในท้องถิ่นช่วยให้สิ่งที่จะเป็นนิพจน์ที่ซับซ้อนและยาว

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