globals ต่างจากฐานข้อมูลอย่างไร?


250

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

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

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


117
มันเป็นเรื่องดีที่จะเห็นสมาชิกทหารผ่านศึกท้าทายความประพฤติเล็ก ๆ น้อย ๆ ...
svidgen

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

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

42
ฐานข้อมูลก็ชั่วร้ายเช่นกัน
เฮมเมอร์

27
มันสนุกที่จะ "กลับ" อาร์กิวเมนต์ที่คุณทำที่นี่และไปในทิศทางอื่น struct ที่มีตัวชี้ไปยังโครงสร้างอื่นนั้นมีเหตุผลเป็นเพียงคีย์ต่างประเทศในหนึ่งแถวของตารางหนึ่งที่คีย์ไปยังแถวอื่นของตารางอื่น การทำงานกับรหัสใด ๆรวมถึงการเดินลิงก์นั้นแตกต่างจากการจัดการข้อมูลในฐานข้อมูลอย่างไร คำตอบ: ใช่ คำถาม: ทำไมเราต้องจัดการโครงสร้างข้อมูลในหน่วยความจำและโครงสร้างข้อมูลในฐานข้อมูลโดยใช้เครื่องมือที่แตกต่างกัน? คำตอบ: ฉันไม่รู้จริง ๆ ! ดูเหมือนว่าจะเกิดอุบัติเหตุในประวัติศาสตร์มากกว่าการออกแบบที่ดี
Eric Lippert

คำตอบ:


118

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

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

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

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

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


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

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

24
2536 ปัญหาเหล่านี้มีปัญหาน้อยกว่า ผู้เขียนทำงานบนระบบตัวประมวลผลเดียวโดยจำลองการโต้ตอบของวัตถุ 1,000 รายการ ในระบบที่ทันสมัยคุณอาจต้องทำการจำลองแบบนั้นอย่างน้อยที่สุดเป็นระบบ dual-core แต่มีแนวโน้มว่ามันอาจมีอย่างน้อย 6 คอร์ในระบบเดียว สำหรับปัญหาที่มีขนาดใหญ่กว่าคุณยังคงเรียกใช้บนคลัสเตอร์ สำหรับการเปลี่ยนแปลงประเภทนี้คุณต้องหลีกเลี่ยงสถานะโลกเนื่องจากรัฐโลกไม่สามารถแบ่งปันได้อย่างมีประสิทธิภาพ
จูลส์

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

5
@ DavidHammen "ยังมีวัตถุบางอย่างที่รู้อย่างน้อยเกี่ยวกับวัตถุทุกอย่างในเกม" ไม่จำเป็นต้องเป็นจริง เทคนิคที่สำคัญในการจำลองการกระจายที่ทันสมัยคือการใช้ประโยชน์จากสถานที่ตั้งและการประมาณเช่นว่าวัตถุที่อยู่ห่างไกลไม่จำเป็นต้องรู้เกี่ยวกับทุกสิ่งที่อยู่ไกลออกไปเฉพาะสิ่งที่ข้อมูลจะถูกส่งไปยังพวกเขาโดยเจ้าของของวัตถุที่ห่างไกล
JAB

75

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

สั้นมากทำให้สถานะของโปรแกรมไม่แน่นอน

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

นอกจากนี้สถานะทั่วโลกทำให้อ่านรหัสของคุณไม่ได้

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

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

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


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

1
@ l0b0 ทรานแซคชันเป็นกลไกที่ทำให้บรรลุเป้าหมายของกรดมากที่สุดถูกต้อง แต่อินเทอร์เฟซ DB ทำให้โค้ดชัดเจนขึ้นโดยนำข้อมูลเข้าสู่ขอบเขตภายในมากขึ้น ลองใช้ JDBC RecordSet กับบล็อก try-with-resources หรือฟังก์ชั่น ORM ที่รับข้อมูลชิ้นส่วนโดยใช้การเรียกใช้ฟังก์ชันเดียว เปรียบเทียบสิ่งนี้กับการจัดการข้อมูลที่อยู่ห่างไกลจากรหัสที่คุณกำลังอ่านในระดับโลก

1
ดังนั้นมันก็โอเคที่จะใช้ตัวแปรทั่วโลกถ้าฉันคัดลอกค่าไปยังตัวแปรท้องถิ่น (ด้วย mutex) ที่จุดเริ่มต้นของฟังก์ชั่นปรับเปลี่ยนตัวแปรท้องถิ่นแล้วคัดลอกค่ากลับไปที่ตัวแปรทั่วโลกในตอนท้ายของ ฟังก์ชั่น? ( ... เขาถามรำพึง.)
RM

1
@RM เขาพูดถึงสองจุด สิ่งที่คุณขว้างออกมาอาจกล่าวถึงสิ่งแรก (ไม่สามารถคาดเดาสถานะของโปรแกรม) ได้ แต่จะไม่พูดถึงสิ่งที่สอง (ความสามารถในการอ่านรหัสของคุณ) ความจริงแล้วอาจทำให้โปรแกรมของคุณอ่านได้แย่ลง: P
riwalk

1
@RM ฟังก์ชั่นของคุณจะทำงานอย่างต่อเนื่องใช่ แต่คุณจะมีคำถามว่ามีสิ่งใดที่แก้ไขตัวแปรโกลบอลในระหว่างนี้และการแก้ไขนั้นสำคัญกว่าสิ่งที่คุณเขียน ฐานข้อมูลอาจมีปัญหาเดียวกันด้วยเช่นกัน
เกรแฮม

45

ฉันขอเสนอข้อสังเกตเล็กน้อย:

ใช่ฐานข้อมูลเป็นสถานะโกลบอล

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

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

อืม ... นี่คือสิ่งที่:

หากโมดูลไม่ทำงานภายนอกสิ่งใดก็ไม่ทำอะไรเลย

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

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

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

แต่โดยทั่วไปเราไม่ได้ทำงานโดยตรงกับรัฐทั่วโลก

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

และในกรณีที่เราจำเป็นต้องเปลี่ยนแปลงสถานะโลกนั้นภายใต้สมมติฐานที่ว่าข้อมูลที่เราได้รับนั้นไม่เปลี่ยนแปลงเรามักจะสามารถทำการล็อคแบบเดียวกับที่เราทำกับโลกท้องถิ่นของเรา

และในที่สุดเรามักจะทำสิ่งที่แตกต่างกับฐานข้อมูลมากกว่าที่เราอาจจะมี globals ซน

โลกที่ซุกซนและแตกสลายมีลักษณะเช่นนี้:

Int32 counter = 0;

public someMethod() {
  for (counter = 0; counter < whatever; counter++) {
    // do other stuff.
  }
}

public otherMethod() {
  for (counter = 100; counter < whatever; counter--) {
    // do other stuff.
  }
}

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


3
วิธีการรับประกัน (เนื่องจากเราไม่สามารถคาดเดาได้) "ว่าข้อมูลที่เราได้รับไม่เปลี่ยนแปลง" ในฐานข้อมูลจะเป็นธุรกรรม
l0b0

ใช่ ... นั่นควรจะบอกเป็นนัยกับ "ล็อคแบบเดียวกัน - แบบเดียวกัน"
svidgen

แต่มันอาจเป็นเรื่องยากที่จะคิดอย่างรอบคอบในตอนท้ายของวัน

ใช่ฐานข้อมูลเป็นสถานะโกลบอล - ซึ่งเป็นเหตุผลว่าทำไมการดึงดูดให้แบ่งปันข้อมูลโดยใช้บางอย่างเช่น git หรือ ipfs
วิลเลียมเพน

21

ฉันไม่เห็นด้วยกับการเรียกร้องพื้นฐานที่:

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

ความคิดเริ่มต้นของฉันคือ "ว้าว Just Just Wow" มีการใช้เวลาและความพยายามอย่างมากในการพยายามหลีกเลี่ยงสิ่งนี้ - และค้นหาว่าการแลกเปลี่ยนและการประนีประนอมใดที่ใช้ได้ผลกับแต่ละแอปพลิเคชัน การเพิกเฉยมันเป็นสูตรสำหรับภัยพิบัติ

แต่ฉันก็แยกตัวออกจากระดับสถาปัตยกรรม ตัวแปรโกลบอลไม่ใช่แค่สภาวะโกลบอล เป็นรัฐระดับโลกที่สามารถเข้าถึงได้จากทุกที่อย่างโปร่งใส ในทางตรงกันข้ามกับการใช้ฐานข้อมูลคุณจำเป็นต้องมีการจัดการกับมัน - (เว้นแต่คุณจะเก็บกว่าการจัดการในตัวแปรทั่วโลก .... )

ตัวอย่างเช่นการใช้ตัวแปรโกลบอลอาจมีลักษณะเช่นนี้

int looks_ok_but_isnt() {
  return global_int++;
}

int somewhere_else() {
  ...
  int v = looks_ok_but_isnt();
  ...
}

แต่การทำสิ่งเดียวกันกับฐานข้อมูลจะต้องชัดเจนยิ่งขึ้นเกี่ยวกับสิ่งที่มันทำ

int looks_like_its_using_a_database( MyDB * db ) {
   return db->get_and_increment("v");
}

int somewhere_else( MyBD * db ) { 
   ...
   v = looks_like_its_using_a_database(db);
   ...
}

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

int looks_like_it_uses_explicit_state( MyState * state ) {
   return state->v++;
}


int somewhere_else( MyState * state ) { 
   ...
   v = looks_like_it_uses_explicit_state(state);
   ...
}

ดังนั้นฉันจะโต้แย้งการใช้ฐานข้อมูลเป็นเหมือนการใช้สถานะที่ชัดเจนมากกว่าการใช้ตัวแปรทั่วโลก


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

1
+1 เธรดที่แตกต่างกันหรือแอปที่เขียนและอ่านจากฐานข้อมูลเดียวกันเป็นแหล่งที่มาของปัญหาที่รู้จักกันดีจำนวนมากซึ่งเป็นเหตุผลว่าทำไมจึงควรมีกลยุทธ์ในการจัดการกับปัญหานี้ไม่ว่าจะในระดับฐานข้อมูลหรือแอป ทั้งสอง ดังนั้นจึงไม่เป็นความจริงที่คุณ (นักพัฒนาแอป) ไม่สนใจว่าใครกำลังอ่านหรือเขียนจากฐานข้อมูล
Andres F.

1
+1 ในหมายเหตุด้านคำตอบนี้จะอธิบายสิ่งที่ฉันเกลียดมากที่สุดเกี่ยวกับการฉีดพึ่งพา มันซ่อนการพึ่งพาประเภทนี้
jpmc26

@ jpmc26 ฉันอาจทำเครื่องหมายคำ แต่ไม่ใช่ตัวอย่างที่ดีของวิธีการฉีดการพึ่งพา (เมื่อเทียบกับการค้นหาทั่วโลก) ช่วยให้การอ้างอิงชัดเจน? ดูเหมือนว่าฉันชอบที่คุณจะมีปัญหากับ API บางอย่างเช่นเวทมนตร์คำอธิบายประกอบที่ใช้โดย JAX-RS และ Spring
Emil Lundberg

2
@EmilLundberg ไม่ปัญหาคือเมื่อคุณมีลำดับชั้น การพึ่งพาการฉีดซ่อนการพึ่งพาของชั้นล่างจากรหัสในระดับที่สูงขึ้นทำให้มันยากที่จะติดตามสิ่งที่โต้ตอบ ตัวอย่างเช่นถ้าMakeNewThingขึ้นอยู่กับMakeNewThingInDbและคลาสคอนโทรลเลอร์ของฉันใช้MakeNewThingแล้วมันไม่ชัดเจนจากรหัสในคอนโทรลเลอร์ที่ฉันกำลังแก้ไขฐานข้อมูล ดังนั้นแล้วสิ่งที่ถ้าผมใช้ระดับที่จริงอีกกระทำธุรกรรมปัจจุบันของฉันไปที่ฐานข้อมูลหรือไม่ DI ทำให้ยากต่อการควบคุมขอบเขตของวัตถุ
jpmc26

18

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

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

ตัวอย่างเช่น:

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

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


1
ฮะ. คุณเอาชนะฉันในขณะที่ฉันครึ่งทางผ่านการเขียนคำตอบที่เหมือนกันเกือบ :)
จูลส์

@Jules คำตอบของคุณให้รายละเอียดเพิ่มเติมจากแอปพลิเคชันของสิ่งต่าง ๆ ; เก็บมันไว้.
Jeffrey Sweeney

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

สวัสดีคุณยังสามารถใช้คะแนน 1 และ 3 ได้หากคุณใช้ภาษาที่พิมพ์แบบคงที่เช่น Java หรือไม่
Jesvin Jose

@aitchnyu ไม่จำเป็น จุดที่ทำคือฐานข้อมูลถูกสร้างขึ้นเพื่อวัตถุประสงค์ในการแบ่งปันข้อมูลที่เชื่อถือได้โดยที่ตัวแปรทั่วโลกไม่ได้ วัตถุที่ใช้อินเทอร์เฟซการทำเอกสารด้วยตนเองในภาษาที่เข้มงวดมีจุดประสงค์ที่แตกต่างจากฐานข้อมูล NoSQL ที่พิมพ์ผิด
Jeffrey Sweeney

10

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

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

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

ด้วยตัวแปรทั่วโลกในทางกลับกันมันไม่ชัดเจนเลย API foo(this_argument, that_argument)ที่กล่าวว่าจะเรียก ไม่มีสิ่งใดในลำดับการโทรที่บอกว่าตัวแปรโกลบอลg_DangerWillRobinsonควรถูกตั้งค่าเป็นค่าบางอย่าง แต่ก่อนการโทรfoo(หรือตรวจสอบหลังจากการโทรfoo)


Google ห้ามการใช้อาร์กิวเมนต์อ้างอิงที่ไม่ใช่แบบ const ใน C ++ เป็นหลักเนื่องจากไม่ชัดเจนสำหรับผู้อ่านของรหัสที่foo(x)จะเปลี่ยนxเพราะfooใช้การอ้างอิงแบบไม่คงที่เป็นอาร์กิวเมนต์ (เปรียบเทียบกับ C # ซึ่งกำหนดว่าทั้งคำจำกัดความของฟังก์ชั่นและไซต์การโทรต้องมีคุณสมบัติพารามิเตอร์อ้างอิงด้วยrefคำหลัก) ในขณะที่ฉันไม่เห็นด้วยกับมาตรฐานของ Google ในเรื่องนี้ฉันเข้าใจประเด็นของพวกเขา

โค้ดถูกเขียนครั้งเดียวและแก้ไขสองสามครั้ง แต่ถ้ามันดีอ่านได้หลายครั้งหลายครั้ง สายการสื่อสารที่ซ่อนอยู่นั้นเป็นกรรมที่เลวร้ายมาก การอ้างอิงที่ไม่ใช่ const ของ C ++ แสดงถึงสายการสื่อสารที่ซ่อนอยู่เล็กน้อย API ที่ดีหรือ IDE ที่ดีจะแสดงให้ฉันเห็นว่า "โอ้นี่คือการโทรโดยการอ้างอิง" ตัวแปรทั่วโลกเป็นสายการสื่อสารที่ซ่อนอยู่ขนาดใหญ่


คำตอบของคุณสมเหตุสมผลมากขึ้น
Billal Begueradj

8

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


8

ในฐานะวิศวกรซอฟต์แวร์ที่ทำงานด้วยเฟิร์มแวร์แบบฝังตัวฉันมักใช้ตัวแปรทั่วโลกสำหรับทุกสิ่งที่เกิดขึ้นระหว่างโมดูล ในความเป็นจริงมันเป็นวิธีที่ดีที่สุดสำหรับการฝังตัว พวกเขาได้รับมอบหมายแบบคงที่ดังนั้นจึงไม่มีความเสี่ยงในการเป่าฮีป / สแต็กและไม่มีเวลาเพิ่มเติมสำหรับการจัดสรรสแต็ก / ล้างข้อมูลในการเข้า / ออกฟังก์ชั่น

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

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

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


7

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

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

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

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

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

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

PS: มีแง่มุมอื่น ๆ ที่มีความสำคัญต่อการเปรียบเทียบนี้เช่นว่ามีส่วนเกี่ยวข้องกับการเห็นพ้องด้วยหรือไม่


ฉันชอบที่คุณเอาสิ่งนี้มาจากมุมการพึ่งพา
cbojar

6

โอเคเรามาเริ่มจากจุดประวัติศาสตร์กันก่อน

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

นี่หมายความว่าการเกลียดชังทั่วโลกเป็นเรื่องของอดีตหรือไม่? ไม่มาก

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

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

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

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

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

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

แน่นอนนี่ไม่ได้หมายความว่าการกำหนดขอบเขตโลกเป็นความชั่วร้าย มันไม่ควรจะเป็นทางออกแรกที่คุณทำ - เป็นตัวอย่างทั่วไปของ "ง่ายต่อการใช้งานและยากที่จะรักษา"


ฟังดูเหมือนโลกทางกายภาพ: ยากที่จะย้อนกลับ

นี่เป็นคำตอบที่ดี แต่สามารถยืนแถลงการณ์วิทยานิพนธ์ (TL; DR section) ได้ตั้งแต่ต้น
jpmc26

6

ตัวแปรทั่วโลกเป็นเครื่องมือมันสามารถใช้ดีและชั่ว

ฐานข้อมูลเป็นเครื่องมือสามารถใช้ดีและชั่วได้

ในฐานะที่เป็นโปสเตอร์ต้นฉบับบันทึกความแตกต่างไม่ได้เป็นสิ่งที่ใหญ่

นักเรียนที่ไม่มีประสบการณ์มักจะคิดว่าข้อบกพร่องเป็นสิ่งที่เกิดขึ้นกับคนอื่น ครูใช้ "ตัวแปรทั่วโลกเป็นสิ่งชั่วร้าย" เป็นเหตุผลง่าย ๆ ที่จะลงโทษการออกแบบที่ไม่ดี โดยทั่วไปนักเรียนไม่เข้าใจว่าเพียงเพราะโปรแกรม 100 บรรทัดของพวกเขาปราศจากข้อผิดพลาดไม่ได้หมายความว่าวิธีเดียวกันนี้สามารถใช้กับโปรแกรม 10,000 บรรทัดได้

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

ถ้าคนใช้วิธีกรดกับตัวแปรทั่วโลกพวกเขาจะไม่เลว

ในทางกลับกันถ้าคุณออกแบบฐานข้อมูลไม่ดีพวกเขาอาจเป็นฝันร้าย


3
การเรียกร้องของนักเรียนโดยทั่วไปเกี่ยวกับ stackoverflow: ช่วยฉันด้วย! รหัสของฉันสมบูรณ์แบบ แต่มันใช้งานไม่ได้!
David Hammen

"วิธี ACID ถึงตัวแปรทั่วโลก" - ดูอ้างอิงใน Clojure
Charles Duffy

@ DavidHammen และคุณคิดว่ามืออาชีพมีสมองที่ไม่เหมือนนักเรียนใช่ไหม
Billal Begueradj

@BillalBEGUERADJ - นั่นคือความแตกต่างระหว่างมืออาชีพและนักเรียน เรารู้ว่าแม้จะมีประสบการณ์มาหลายปีและแม้จะมีความพยายามอย่างดีที่สุดในการตรวจสอบโค้ดการทดสอบและอื่น ๆ แต่โค้ดของเรานั้นไม่สมบูรณ์แบบ
David Hammen


5

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


3
ตัวอย่างเช่นerrnoใน C.
David Hammen

1
สิ่งนี้อธิบายได้อย่างชัดเจนว่าทำไม globals และฐานข้อมูลจึงไม่เหมือนกัน อาจมีความแตกต่างอื่น ๆ แต่การโพสต์เฉพาะของคุณจะทำลายแนวคิดทั้งหมด หากคุณให้ตัวอย่างรหัสอย่างรวดเร็วฉันแน่ใจว่าคุณจะได้รับ upvotes มากมาย เช่น MyFunc () {x = globalVar * 5; // .... การประมวลผลอื่น ๆ ; y = globalVar * 34; // Ooops, เธรดอื่น ๆ อาจมีการเปลี่ยนแปลง globalVar ในระหว่างการประมวลผลอื่น ๆ และ x และ y กำลังใช้ค่าที่แตกต่างกันสำหรับ globalVar ในการคำนวณของพวกเขาซึ่งแน่นอนว่าจะไม่ได้ผลลัพธ์ที่ต้องการ
Dunk

5

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

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

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

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


* ข้อยกเว้นที่นี่คือนักเรียน มันสมเหตุสมผลที่จะห้ามนักเรียนไม่ให้ใช้ตัวแปรทั่วโลกดังนั้นพวกเขาจึงต้องเรียนรู้ว่าทางเลือกคืออะไร

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


2

ในความหมายความแตกต่างระหว่างตัวแปรทั่วโลกและฐานข้อมูลจะคล้ายกับความแตกต่างระหว่างสมาชิกส่วนตัวและสาธารณะของวัตถุ (สมมติว่าใครยังคงใช้เขตข้อมูลสาธารณะ) หากคุณคิดว่าโปรแกรมทั้งหมดเป็นวัตถุแล้ว globals เป็นตัวแปรส่วนตัวและฐานข้อมูลเป็นเขตข้อมูลสาธารณะ

ความแตกต่างที่สำคัญที่นี่เป็นหนึ่งในความรับผิดชอบ

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

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

เมื่อมัลติเธรดเข้ามาเล่นแนวคิดของฐานข้อมูลส่วนกลาง v / s สาธารณะ v / s ทั่วโลก v / s เป็นเพียงความแตกต่างตามสเปกตรัม

static int global; // within process memory space
static int dbvar; // mirrors/caches data outside process memory space

class Cls {
    public: static int class_public; // essentially the same as global
    private: static int class_private; // but public to all methods in class

    private: static void method() {
        static int method_private; // but public to all scopes in method
        // ...
        {
            static int scope1_private; // mutex guarded
            int the_only_truly_private_data;
        }
        // ...
        {
            static int scope2_private; // mutex guarded
        }
    }
}

1

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

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


0

มีความแตกต่างหลายประการ:

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

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

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

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


0

แน่นอนว่ารูปทรงกลมนั้นไม่เหมาะสมเสมอไป พวกเขามีอยู่เพราะพวกเขามีการใช้งานที่ถูกกฎหมาย ปัญหาหลักของ globals และแหล่งที่มาหลักของการตักเตือนเพื่อหลีกเลี่ยงพวกเขาก็คือรหัสที่ใช้ global นั้นเชื่อมต่อกับหนึ่งและเพียงหนึ่งเดียวทั่วโลก

ตัวอย่างเช่นพิจารณาเซิร์ฟเวอร์ HTTP ที่จัดเก็บชื่อเซิร์ฟเวอร์

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

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

ดังนั้นการคัดค้านหลักถึง globals มีเพียงค่าเดียวสำหรับรหัสทั้งหมดที่เข้าถึงระดับโลกนั้นไม่ได้ใช้กับรายการฐานข้อมูล รหัสเดียวกันสามารถเข้าถึงอินสแตนซ์ฐานข้อมูลที่แตกต่างกันซึ่งมีค่าแตกต่างกันสำหรับรายการเฉพาะได้อย่างง่ายดาย


0

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

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

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


0

ฉันจะคิดเกี่ยวกับมันแตกต่างกันเล็กน้อย: "ตัวแปรทั่วโลก" เช่นพฤติกรรมเป็นราคาที่จ่ายโดยผู้ดูแลระบบฐานข้อมูล (DBAs) เพราะมันเป็นความชั่วร้ายที่จำเป็นในการทำงานของพวกเขา

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

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

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

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

ไม่ใช่เรื่องแปลกที่จะมีแพ็คเกจซอฟต์แวร์ 100k line ในทางทฤษฎีบรรทัดใด ๆ ในซอฟต์แวร์อาจมีผลกระทบต่อโลกในเวลาใดก็ได้ ใน DBA คุณจะไม่พบข้อความค้นหาต่าง ๆ 100k ที่สามารถแก้ไขฐานข้อมูลได้ นั่นจะไม่มีเหตุผลที่จะรักษาด้วยความใส่ใจในรายละเอียดที่จำเป็นในการปกป้องคุณจากตัวคุณเอง หาก DBA มีอะไรที่ใหญ่กว่านี้พวกเขาจะใส่ข้อมูลในฐานข้อมูลโดยใช้ accessors เพื่อหลีกเลี่ยงปัญหา "global like" และทำการทำงานให้มากที่สุดเท่าที่จะทำได้ผ่านกลไก "ปลอดภัย" ดังนั้นเมื่อการผลักดันเข้ามาถึงแม้คนฐานข้อมูลจะหลีกเลี่ยงการกลมกลืน พวกเขาก็มาที่มีจำนวนมากของอันตรายและมีทางเลือกที่มีเพียงแค่เป็นที่แข็งแกร่ง แต่ไม่เป็นอันตราย

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


0

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

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


-2

ลูกโลกนั้นไม่ชั่ว พวกเขาเป็นเพียงเครื่องมือ MISUSE of globals นั้นเป็นปัญหาเช่นเดียวกับการใช้งานผิดพลาดของคุณสมบัติการเขียนโปรแกรมอื่น ๆ

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


บางคนในกลุ่มดาวรุ่งจะนึกถึงคำอธิบายของคุณบ้างไหม? ดูเหมือนหยาบคายที่จะลงคะแนนเสียงโดยไม่มีคำอธิบาย
Byron Jones

-2

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

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