นี่คือหนึ่งใน "ควร" แทนที่จะเป็น "มาตรฐาน" ชนิดของการเข้ารหัส เหตุผลก็คือคุณจะต้องเขียนโปรแกรมแยกวิเคราะห์ C ++ เพื่อบังคับใช้
กฎที่พบบ่อยมากสำหรับไฟล์ส่วนหัวคือพวกเขาจะต้องยืนด้วยตนเอง ไฟล์ส่วนหัวต้องไม่กำหนดให้ไฟล์ส่วนหัวอื่น ๆ รวม #included ก่อนที่จะรวมส่วนหัวที่เป็นปัญหา นี่คือข้อกำหนดที่สามารถทดสอบได้ รับส่วนหัวสุ่มบางส่วนfoo.hh
ต่อไปนี้ควรรวบรวมและเรียกใช้:
#include "foo.hh"
int main () {
return 0;
}
กฎนี้มีผลที่ตามมาเกี่ยวกับการใช้คลาสอื่นในบางหัวข้อ บางครั้งผลกระทบเหล่านั้นสามารถหลีกเลี่ยงได้โดยการส่งต่อประกาศคลาสอื่น ๆ เหล่านั้น ไม่สามารถทำได้ด้วยคลาสไลบรารีมาตรฐานจำนวนมาก ไม่มีทางที่จะไปข้างหน้าประกาศ instantiation แม่แบบเช่นไม่ได้หรือstd::string
std::vector<SomeType>
คุณต้องใช้#include
ส่วนหัว STL เหล่านั้นในส่วนหัวแม้ว่าการใช้ชนิดเท่านั้นจะเป็นอาร์กิวเมนต์ของฟังก์ชัน
ปัญหาอื่นคือสิ่งที่คุณลากเข้ามาโดยบังเอิญตัวอย่าง: พิจารณาสิ่งต่อไปนี้:
ไฟล์ foo.cc:
#include "foo.hh"
#include "bar.hh"
void Foo::Foo () : bar() { /* body elided */ }
void Foo::do_something (int item) {
...
bar.add_item (item);
...
}
นี่bar
เป็นชั้นข้อมูลสมาชิกที่เป็นประเภทFoo
Bar
คุณได้ทำสิ่งที่ถูกต้องที่นี่และได้ # รวม bar.hh Foo
แม้ว่าที่จะต้องได้รับการรวมอยู่ในส่วนหัวที่กำหนดระดับ แต่คุณยังไม่ได้รวมสิ่งที่ใช้โดยและBar::Bar()
Bar::add_item(int)
มีหลายกรณีที่การเรียกเหล่านี้อาจส่งผลให้มีการอ้างอิงภายนอกเพิ่มเติม
หากคุณวิเคราะห์foo.o
ด้วยเครื่องมือเช่นnm
นั้นจะปรากฏว่าฟังก์ชั่นในการเรียกร้องทุกชนิดของสิ่งที่คุณยังไม่ได้ดำเนินการที่เหมาะสมfoo.cc
#include
ดังนั้นคุณควรเพิ่ม#include
คำสั่งสำหรับการอ้างอิงภายนอกโดยบังเอิญfoo.cc
? คำตอบนั้นไม่แน่นอน ปัญหาคือว่ามันยากมากที่จะแยกแยะฟังก์ชั่นเหล่านั้นที่เรียกว่าบังเอิญจากฟังก์ชั่นที่เรียกโดยตรง