================================================================
typedef struct {
union {
struct {
char fn[5];
char ln[5];
} fullname;
char name[5+5+1];
}
unsigned int age;
unsigned int area_code;
} my_struct;以上这些都是我无法控制的结构。我个人不是一个粉丝,但这个结构是“合法的”。
================================================================
我的代码:
void caller {
my_struct str;
str = (my_struct){}; //initialise
fill(&str);
printf("%s [%s/%s]\n", str.name, str.fullname.fn, str.fullname.ln); // PROBLEM!
}
void fill(my_struct * str) {
//first name
printf("Enter first name: ");
fgets(str.fullname.fn, sizeof(str.fullname.fn), stdin);
if (str.fullname.fn[strlen(str.fullname.fn) - 1] == '\n')
str.fullname.fn[strlen(str.fullname.fn) - 1] = '\0';
//last name
printf("Enter last name: ");
fgets(str.fullname.ln, sizeof(str.fullname.fn), stdin);
if (str.fullname.ln[strlen(str.fullname.ln) - 1] == '\n')
str.fullname.ln[strlen(str.fullname.ln) - 1] = '\0';
sprintf(str.name, "%s %s", str.fullname.fn, str.fullname.ln);
printf("Age: ");
scanf("%ud", &str.age);
getchar();
printf("Area Code: ");
scanf("%ud", &str.area_code);
getchar();
}================================================================
如果输入是:
// PROBLEM的打印输出如下:
joe moe [joe moe/oe]而不是
joe moe [joe/moe]有什么想法吗?我不知道为什么fn和ln的价值在改变.
发布于 2011-07-15 19:26:40
问题是name和fullname共享内存(因为union)。所以
sprintf(str.name, "%s %s", str.fullname.fn, str.fullname.ln);还可以在fn和ln上编写。
这是个不错的问题,但我不知道该如何彻底解决这个问题。我会这样做的:摆脱上面的sprintf,然后自己做。
void caller
{
fill(&str);
printf("%s %s [%s/%s]\n", str.fullname.fn, str.fullname.ln, str.fullname.fn, str.fullname.ln);
}发布于 2011-07-15 19:40:10
问题在于:
sprintf(str.name, "%s %s", str.fullname.fn, str.fullname.ln);sprintf不能对重叠的内存区域进行操作。
您可以做的是不把\0放在名字后面,而是用空格代替\n,只打印str.name。
另外,使用' ' (空格)初始化数组,它将为小于5个字符的第一个名称提供输入。
memset(&str, ' ', sizeof(str));发布于 2011-07-15 19:28:21
这个结构的名称部分是一个联合,所以它要么是name,要么是fullname,但不是同时使用。因此,在设置名称后,字段全名无效。工会的问题在于,您必须提供一个机制来检测实际使用的联合的哪一部分。我看不出这里有什么东西可以决定是用名字还是全名。
https://stackoverflow.com/questions/6712124
复制相似问题