如何在C编程中访问不完整类型的成员
假设在我的如何在C编程中访问不完整类型的成员,c,C,假设在我的child.h文件中声明了以下不完整类型 typedef struct child * child_ptr; struct child { char * type; int age; }; // some code before the main int main( void ) { struct child *child = new_child( "Boy", 5 ); child->type; // i know i will get an e
child.h
文件中声明了以下不完整类型
typedef struct child * child_ptr;
struct child {
char * type;
int age;
};
// some code before the main
int main( void ) {
struct child *child = new_child( "Boy", 5 );
child->type; // i know i will get an error
}
我的child.c
文件中有不完整的完整类型定义
typedef struct child * child_ptr;
struct child {
char * type;
int age;
};
// some code before the main
int main( void ) {
struct child *child = new_child( "Boy", 5 );
child->type; // i know i will get an error
}
假设这是我的main.c
文件
typedef struct child * child_ptr;
struct child {
char * type;
int age;
};
// some code before the main
int main( void ) {
struct child *child = new_child( "Boy", 5 );
child->type; // i know i will get an error
}
不同于C++、爪哇、C、C,C对封装类型的支持有限。C为封装提供的唯一工具是不完整类型。这些类型描述对象,但缺少确定其大小所需的信息。这就是为什么编译程序后会出现错误的原因。那么,有没有办法访问它们
我认为,一种方法是在我的
child.h
文件中声明“public”函数。例如,一个函数,它获取指向子对象的指针并返回存储在“type”成员变量中的值;但是,这将防止数据隐藏。如果我将结构移动到child.h
文件中,默认情况下所有成员都是public。同样,这将防止数据隐藏。您可以在child.h
文件中创建函数原型,它将struct child*
作为参数,并返回不同的成员
例如:
char * get_name(child_ptr chld);
在child.c
文件中,可以看到struct child
的定义,并在main.c
文件中使用它,如下所示:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
您可以在
child.h
文件中创建函数原型,它将struct child*
作为参数,并返回不同的成员
例如:
char * get_name(child_ptr chld);
在child.c
文件中,可以看到struct child
的定义,并在main.c
文件中使用它,如下所示:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
您可以在
child.h
文件中创建函数原型,它将struct child*
作为参数,并返回不同的成员
例如:
char * get_name(child_ptr chld);
在child.c
文件中,可以看到struct child
的定义,并在main.c
文件中使用它,如下所示:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
您可以在
child.h
文件中创建函数原型,它将struct child*
作为参数,并返回不同的成员
例如:
char * get_name(child_ptr chld);
在child.c
文件中,可以看到struct child
的定义,并在main.c
文件中使用它,如下所示:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
在child.h中,提供所有公共成员的定义(并使他们在定义中处于首位) 你不需要让任何人接触你孩子的私人部位,如果你不想让任何人碰它们,我也不会。这只是为了证明你在这里看到的类型还有更多 在child.c中,创建另一个类似的类型:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
您可以在这里看到一些示例,说明如何使用private_child创建新的子级,以及如何通过cast访问child.c中的私有成员。
这将始终有效,因为
(C1x§6.7.2.1.13:“指向经过适当转换的结构对象的指针指向其
初始成员…反之亦然。as结构中可能有未命名的填充
对象,但不是在其开头。”)
编辑
在旧版本的C中,flexible length数组成员可能不可用,您可以忽略子元素的该成员。这个数组实际上使您(可能)想要的类型不完整,因此没有人会意外地尝试在自动存储中创建其中一个类型(它只能通过分配来创建,希望只能使用指定的“构造函数”)。我不确定是否有其他方法可以使C中的类型不完整。在child.h中提供所有公共成员的定义(并使他们在定义中排在第一位) 你不需要让任何人接触你孩子的私人部位,如果你不想让任何人碰它们,我也不会。这只是为了证明你在这里看到的类型还有更多 在child.c中,创建另一个类似的类型:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
您可以在这里看到一些示例,说明如何使用private_child创建新的子级,以及如何通过cast访问child.c中的私有成员。
这将始终有效,因为
(C1x§6.7.2.1.13:“指向经过适当转换的结构对象的指针指向其
初始成员…反之亦然。as结构中可能有未命名的填充
对象,但不是在其开头。”)
编辑
在旧版本的C中,flexible length数组成员可能不可用,您可以忽略子元素的该成员。这个数组实际上使您(可能)想要的类型不完整,因此没有人会意外地尝试在自动存储中创建其中一个类型(它只能通过分配来创建,希望只能使用指定的“构造函数”)。我不确定是否有其他方法可以使C中的类型不完整。在child.h中提供所有公共成员的定义(并使他们在定义中排在第一位) 你不需要让任何人接触你孩子的私人部位,如果你不想让任何人碰它们,我也不会。这只是为了证明你在这里看到的类型还有更多 在child.c中,创建另一个类似的类型:
child_ptr chld = new_child( "Boy", 5 );
char* child_name = get_name(chld);
struct private_child{
struct child;
/*private members*/
};
struct child *new_child(/*Init Params*/){
struct private_child *tmp = malloc(sizeof *tmp);
/* Initialize the child */
return &tmp->child;
}
void use_child(const child *c){
struct private_child *pc = (struct private_child *)c;
/*access the private members*/
}
您可以在这里看到一些示例,说明如何使用private_child创建新的子级,以及如何通过cast访问child.c中的私有成员。
这将始终有效,因为
(C1x§6.7.2.1.13:“指向经过适当转换的结构对象的指针指向其
初始成员…反之亦然。as结构中可能有未命名的填充
对象,但不是在其开头。”)
编辑
在旧版本的C中,flexible length数组成员可能不可用,您可以忽略子元素的该成员。这个数组实际上使您(可能)想要的类型不完整,因此没有人会意外地尝试在