1

我得到了一个程序的外壳,并且必须填写一些功能。

我有两个自动创建并传递给我必须定义的函数的结构。

typedef struct {
    char data[20];
} msg;

typedef struct {
     int seqnum;
     int acknum;
     int checksum;
     char payload[20];
 } pkt;

假设我必须定义这个函数foo并这样创建它:

void foo(msg message) {
    printf("%s\n", message.data);
}

当调用该函数时,它会打印出ddddddddddddddddddddôÑ@<úHn½*Ìå«*¤ú¤F«*. 除非我错了,它不应该只能容纳20个字符吗?我实际上并没有创建msg.

如果我复制msg.datapkt.payload.

void foo(msg message) {
    pkt packet;
    strncpy(packet.payload, message.data, sizeof(packet.payload));
    printf("%s\n", message.data);
    printf("%s\n", packet.payload);
}

message.data 的打印结果与以前相同,但 packet.payload 的打印结果相同eeeeeeeeeeeeeeeeeeee<úeeeeeeeeeeeeeeeeeeee²+!@<úHn½*Ìå«*¤ú¤F«*。为什么超过20个字符?

这是我第一次使用 C,如果这很明显,请原谅我,但我什至无法触及作业的核心,因为我在语言方面遇到了问题。

4

3 回答 3

2

带有 %s 说明符的 printf() 假定您正在向它发送一个以零结尾的字符串。因此它会读取内存中的字节,直到找到零(或'\0')。

strncpy 不会将零附加到目标字符串,除非在到达 n 个字符之前在源字符串中遇到零(此时目标字符串的其余部分用零填充,这当然会导致它以零结尾) .

于 2010-11-18T02:00:22.467 回答
2

strncpy不会终止正在复制的字符串。

您要么必须手动终止该字段,

strncpy(packet.payload, message.data, sizeof(packet.payload) - 1);
packet.payload[sizeof(packet.payload) - 1] = '\0';
printf("%s\n", message.data);
printf("%s\n", packet.payload);

或将其视为固定大小的可能未终止的字符串:

strncpy(packet.payload, message.data, sizeof(packet.payload));
printf("%s\n", message.data);
printf("%.*s\n", sizeof packet.payload, packet.payload);

或者,您可以使用snprintf(C99) 来终止它,因为它总是终止字符串,因此不太容易出错。

snprintf(packet.payload, sizeof packet.payload, "%s", message.data);
printf("%s\n", message.data);
printf("%s\n", packet.payload);
于 2010-11-18T02:02:55.463 回答
0
strncpy(packet.payload, message.data, sizeof(packet.payload));
packet.payload[sizeof(packet.payload) - 1] = 0;
于 2010-11-18T02:03:13.650 回答