การตรวจสอบสภาพซ้ำซ้อนกับการปฏิบัติที่ดีที่สุดหรือไม่?


16

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

ฉันมีโปรแกรม Python ที่ฉัน ...

  1. ใช้ argparse required=Trueเพื่อบังคับใช้สองอาร์กิวเมนต์ซึ่งเป็นทั้งชื่อไฟล์ ตัวแรกคือชื่อไฟล์อินพุตส่วนที่สองคือชื่อไฟล์เอาต์พุต
  2. มีฟังก์ชั่นreadFromInputFileที่ตรวจสอบก่อนเพื่อดูว่าชื่อไฟล์อินพุตถูกป้อน
  3. มีฟังก์ชั่นwriteToOutputFileที่ตรวจสอบก่อนเพื่อดูว่ามีการป้อนชื่อไฟล์เอาต์พุต

โปรแกรมของฉันมีขนาดเล็กพอที่จะทำให้ฉันเชื่อว่าการตรวจสอบใน # 2 และ # 3 ซ้ำซ้อนและควรถูกลบออกจึงทำให้ทั้งสองฟังก์ชั่นพ้นจากifสภาพที่ไม่จำเป็น อย่างไรก็ตามฉันก็ถูกชักนำให้เชื่อว่า "การตรวจสอบซ้ำสองครั้งก็โอเค" และอาจเป็นคำตอบที่ถูกต้องในโปรแกรมที่สามารถเรียกใช้ฟังก์ชันได้จากตำแหน่งอื่นที่การแยกวิเคราะห์ของอาร์กิวเมนต์ไม่เกิดขึ้น

(นอกจากนี้หากการอ่านหรือเขียนล้มเหลวฉันมีtry exceptในแต่ละฟังก์ชั่นเพื่อเพิ่มข้อความแสดงข้อผิดพลาดที่เหมาะสม)

คำถามของฉันคือดีที่สุดที่จะหลีกเลี่ยงการตรวจสอบสภาพซ้ำซ้อนทั้งหมดหรือไม่ ควรตรรกะของโปรแกรมเป็นของแข็งที่ตรวจสอบต้องทำเพียงครั้งเดียว? มีตัวอย่างที่ดีที่แสดงถึงสิ่งนี้หรือการสนทนาหรือไม่?

แก้ไข: ขอบคุณทุกคำตอบ! ฉันได้เรียนรู้บางอย่างจากแต่ละคน การได้เห็นมุมมองมากมายทำให้ฉันมีความเข้าใจที่ดีขึ้นเกี่ยวกับวิธีแก้ไขปัญหานี้และกำหนดวิธีการแก้ปัญหาตามความต้องการของฉัน ขอขอบคุณ!


นี่เป็นรุ่นทั่วไปอย่างหนักของคำถามของคุณ: softwareengineering.stackexchange.com/questions/19549/... ฉันจะไม่บอกว่ามันซ้ำซ้อนเพราะมันมีจุดรวมที่ค่อนข้างใหญ่กว่า แต่มันอาจช่วยได้
หมอสีน้ำตาล

คำตอบ:


15

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

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

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

หรือเป็นโปรแกรมขนาดเล็กเพียงเพื่อการเรียนรู้หรือเพื่อความสนุกสนาน จากนั้นตรวจสอบซ้ำเหล่านั้นไม่จำเป็น

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

ในที่สุดขอยกตัวอย่างสิ่งที่มีความหมายในกรณีของคุณ สมมติว่าความต้องการของคุณเปลี่ยนไปเป็นอย่างอื่น

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

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


"... ขอบเขตระหว่างส่วนประกอบในรูปแบบของ API สาธารณะ ... "ฉันสังเกตว่า "ขอบเขตของคลาสกระโดด" เพื่อพูด ดังนั้นสิ่งที่จำเป็นคือชั้นเรียน ชั้นโดเมนธุรกิจที่เชื่อมโยงกัน ฉันอนุมานจาก OP นี้ว่าหลักการที่แพร่หลายของ "มันง่ายดังนั้นไม่จำเป็นต้องเรียน" เป็นที่ทำงานที่นี่ อาจมีคลาสที่เรียบง่ายล้อมรอบ "วัตถุหลัก" บังคับใช้กฎเกณฑ์ทางธุรกิจเช่น "ไฟล์จะต้องมีชื่อ" ซึ่งไม่เพียง แต่จะขึ้นอยู่กับรหัสที่มีอยู่ แต่จะทำให้มันแห้งในอนาคต
Radarbob

@radarbob: สิ่งที่ฉันเขียนไม่ได้ จำกัด เฉพาะ OOP หรือส่วนประกอบในรูปแบบของคลาส นอกจากนี้ยังนำไปใช้กับไลบรารีที่กำหนดเองด้วย public API, object oriented หรือไม่
Doc Brown

5

ความซ้ำซ้อนไม่ใช่บาป ความซ้ำซ้อนที่ไม่จำเป็นคือ

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

  2. หากreadFromInputFile()และwriteToOutputFile()ตรวจสอบพารามิเตอร์ด้วยตนเองคุณจะได้รับข้อความแสดงข้อผิดพลาดที่กำหนดเองซึ่งอธิบายถึงความต้องการชื่อไฟล์อีกครั้ง

  3. หากreadFromInputFile()และwriteToOutputFile()ไม่ตรวจสอบพารามิเตอร์ด้วยตนเองจะไม่มีข้อความแสดงข้อผิดพลาดที่กำหนดเองปรากฏขึ้น ผู้ใช้จะต้องค้นหาข้อยกเว้นที่เกิดขึ้นด้วยตนเอง

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

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


4

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

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

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


1

สมมติว่าคุณมีฟังก์ชั่น (ใน C)

void readInputFile (const char* path);

และคุณไม่พบเอกสารใด ๆ เกี่ยวกับเส้นทาง จากนั้นคุณดูการใช้งานและมันบอกว่า

void readInputFile (const char* path)
{
    assert (path != NULL && strlen (path) > 0);

ไม่เพียงแค่ทดสอบอินพุตไปยังฟังก์ชัน แต่ยังบอกผู้ใช้ฟังก์ชันว่าพา ธ ไม่ได้รับอนุญาตให้เป็น NULL หรือสตริงว่าง


0

โดยทั่วไปการตรวจสอบอีกครั้งไม่ได้มักจะดีหรือไม่ดี มีคำถามหลายแง่มุมอยู่เสมอในกรณีเฉพาะของคุณซึ่งเรื่องนั้นขึ้นอยู่กับ ในกรณีของคุณ:

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

0

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

การตรวจสอบมากเกินไปจะไม่เจ็บอาจทำให้น้อยลง

อย่างไรก็ตามหากคุณกำลังตรวจสอบภายในลูปที่ทำซ้ำบ่อยครั้งคุณควรนึกถึงการลบความซ้ำซ้อนแม้ว่าการตรวจสอบตัวเองจะอยู่ในเวลาส่วนใหญ่จะไม่แพงเมื่อเทียบกับสิ่งที่ตามมาหลังจากการตรวจสอบ


และเนื่องจากคุณมีมันอยู่แล้วมันไม่คุ้มค่ากับความพยายามในการถอดออกเว้นแต่จะอยู่ในวงวนหรือบางอย่าง
StarWeaver

0

บางทีคุณสามารถเปลี่ยนมุมมองของคุณ:

หากมีอะไรผิดพลาดผลลัพธ์คืออะไร แอปพลิเคชันของคุณ / ผู้ใช้จะเป็นอันตรายหรือไม่?

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

จากบริบทที่คุณให้:

  • การป้อนข้อมูลไฟล์เดียว
  • ไฟล์เอาต์พุตหนึ่งไฟล์B

ผมถือว่าคุณกำลังทำอะไรเปลี่ยนแปลงจากไปB หากAและBมีขนาดเล็กและการเปลี่ยนแปลงมีขนาดเล็กอะไรคือผลที่ตามมา?

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

2) คุณลืมระบุ outputfile ผลลัพธ์ในสถานการณ์ต่าง ๆ :

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

b) อินพุตอ่านทีละขั้นตอน จากนั้นกระบวนการเขียนจะหยุดเหมือนใน (1) ทันทีและผู้ใช้จะเริ่มต้นใหม่อีกครั้ง

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

นอกจากนี้: คุณควรหลีกเลี่ยงความหวาดระแวงและไม่ควรทำ Doublecheck มากเกินไป


0

ฉันจะยืนยันว่าการทดสอบไม่ได้ซ้ำซ้อน

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

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

โซลูชันที่แข็งแกร่งยิ่งขึ้นจะมีตัวตรวจสอบชื่อไฟล์หนึ่งหรือสองตัว

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

ฉันใช้กฎสองข้อในการดำเนินการเมื่อ:

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

0

การตรวจสอบซ้ำซ้อน การแก้ไขในกรณีนี้ต้องการให้คุณลบ readFromInputFile และ writeToOutputFile และแทนที่ด้วย readFromStream และ writeToStream

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

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

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