发件人:scs@eskimo.com (Steve Summit)
主题:回复:ADT??
日期:1997年9月23日,星期二,18:21:38 -0700 (PDT)
Message-Id:<199709240121.SAA03216@mail.eskimo.com>
...你可能在adt.h中有声明
extern struct adt *newadt(void); extern int processadt(struct adt *); extern void freeadt(struct adt *);
然后一个客户端可以这样做
#include "adt.h" struct adt *theadt = newadt(); processadt(theadt); freeadt(theadt);
ADT的实际实现将从这里开始
#include "adt.h" struct adt { /* actual structure definition */ }; struct adt * newadt(void) { ...
或者,如果ADT的实现包含多个源文件,你可以将结构体定义放在,例如,adtinternals.h:
struct adt { /* actual structure definition */ };
然后,包含这两个文件adt.h和adtinternals.h在实现ADT的每个源文件中
#include "adt.h" #include "adtinternals.h" struct adt * newadt(void) { ...
有时,我发现将与ADT相关的所有声明集中在一个头文件中(“adt.h”,在继续的示例中),这样做是这样的
#ifdef ADT_INTERNALS struct adt { /* actual structure definition */ }; #endif extern struct adt *newadt(void); extern int processadt(struct adt *); extern void freeadt(struct adt *);
然后我定义ADT_INTERNALS在实现ADT的每个源文件中,就在包含adt.h:
#define ADT_INTERNALS #include "adt.h" struct adt * newadt(void) { ...
这显然是一种较弱的信息隐藏形式,因为客户端更容易“作弊”并窥探类型的实现。
最后,当你使用第一种形式,即不完整的结构体类型时,通常将不完整的结构体声明放在公共头文件中是很有用的
struct adt; extern struct adt *newadt(void); extern int processadt(struct adt *); extern void freeadt(struct adt *);
这可以防止某些编译器警告,并避免其他一些晦涩的潜在问题。