我注意到struct
地址和第一个元素地址看起来是相同的。
因此,我尝试使用主struct
的地址访问struct
的第一个元素。
但是我遇到了错误。
与显示器的参数1兼容。
我在这里犯什么错误?
代码
#include <stdio.h>
#include <stdlib.h>
#define BASE(class) *(&class)
struct animal {
int walk;
int hear;
};
struct bird {
struct animal *base;
int fly;
};
void display(struct animal *common) {
printf("All animal details hear=%d walk=%d ", common->hear, common->walk);
}
int main() {
struct bird peacockptr;
struct animal base;
base.hear = 1;
base.walk = 1;
peacockptr.base = &base;
struct bird *pecock = &peacockptr;
pecock->fly = 1;
printf("base address using peacock struct %d\n",
BASE(peacockptr)); // both are printing same address
printf("base address animal %d\n",
&base); // both are printing same address
display(&base); // here it work
display(BASE(peacockptr)); // getting error
}
答案 0 :(得分:3)
的确,结构的地址与其第一个成员的地址相同。但是,它们具有不同的类型。一个具有类型struct animal *
,另一个具有类型struct base *
。
在这种情况下,您可以在两者之间进行转换,但是您需要进行显式强制转换。
display((struct animal *)BASE(peacockptr));
另外,关于定义BASE
宏的方式:
#define BASE(class) *(&class)
*
和&
运算符相互抵消,因此实际上是无操作的。 BASE(peacockptr)
等同于peacockptr
。
现在强制转换失败的原因是,您将peacockptr
定义为实例,将pecock
定义为指针 ,即您对命名感到困惑。切换名称以反映用法:
struct bird peacock;
struct animal base;
base.hear=1;
base.walk=1;
peacock.base= &base;
struct bird *peacockptr =&peacock;
peacockptr->fly=1;
答案 1 :(得分:2)
如前所述,当操作符取消指针时,您可以删除BASE
宏。
我清除并更正了您的代码,并解释了哪里出了问题:
#include <stdio.h>
#include <string.h>
struct animal
{
int walk;
int hear;
};
struct bird
{
struct animal *base;
int fly;
};
void display(struct animal *common)
{
printf("All animal details hear=%d walk=%d\n",common->hear, common->walk);
}
int main()
{
struct bird peacock; // removed ptr suffix, since it is not a pointer
struct animal base ;
base.hear=1;
base.walk=1;
peacock.base= &base;
struct bird *peacockptr = &peacock;
peacockptr->fly=1;
printf("base address using peacock struct %p\n", (void *)*(struct animal **)peacockptr); //This is the address of base using peackockptr
printf("base address animal %p\n", (void *)&base); //This is the address of base
display(&base);
display(*(struct animal **)peacockptr);
return 0;
}
请注意,peackock
的地址等于结构的第一个元素struct animal *
的地址。因此,您必须将peacockptr
强制转换为struct animal **
(因为它指向类型为struct animal *
的第一个元素),然后对其取消引用以获取base
的地址。