0
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

typedef char String[256];

typedef struct LinkedListNode {
String Name;
struct LinkedListNode * Next;
struct LinkedListNode * Friend;
} Node;

typedef Node * NodePointer;


NodePointer InputData(NodePointer Head) {

    String PersonName;
    NodePointer Person;
    int StringLength;
    String FormattedName;
do {    
        printf("Enter nation name :");
        fgets(PersonName,256,stdin);
        if (PersonName[0] != '\n') {
            Person = (NodePointer)malloc(sizeof(NodePointer));
            //copy all except trailing \n
            strncpy(Person->Name, PersonName, strlen(PersonName)-1);
            Person->Next = Head;
            Person->Friend = NULL;
            Head = Person;
        }
    } while (strcmp(PersonName, "\n"));
return Head;
}

void InputAllies(NodePointer Head) {
    String AllyName;
    NodePointer Ally;
    String FormattedName;
    do {    
            printf("Enter best ally for %s :", Head->Name);
            fgets(AllyName,256,stdin);  
            if (AllyName[0] != '\n') {
                Ally = (NodePointer)malloc(sizeof(NodePointer));
                //copy all except trailing \n
                strncpy(Ally->Name, AllyName, strlen(AllyName)-1);
                Head->Friend = Ally;
                Head = Head->Next;
            }
        } while (Head != NULL);
}

段错误的部分具体是 InputAllies() 函数,并且仅适用于具有 5 个或更多元素的列表。我真的不知道发生了什么,但我认为这与我的字符串的大小有关。降低 typedef String 的大小仅在 3 个元素后导致段错误。

4

1 回答 1

4

我认为在函数中InputData,就在之后strncpy,您忘记将 final 添加'\0'到字符串Person->Name中。问题是当您打印字符串时。在您的 Mac 上,似乎有一个空字符恰好神奇地出现在正确的位置;在 Linux 服务器上,你就没那么幸运了。

手册中复制:

strcpy() 函数将 指向的字符串src,包括终止的空字节 ( '\0') 复制到 指向的缓冲区 dest。字符串不能重叠,并且目标字符串 dest 必须足够大以接收副本。

strncpy()功能类似,不同之处在于最多复制的n字节 。 警告:如果 的第一个字节中src没有空字节,则放入的字符串不会以空结尾。nsrcdest

所以你的问题是最后一句话,只有当你的源字符串不能适合n你的目标字符串的第一个字节时才会发生。我认为这正是您的情况,因为您设置n的值小于strlen源字符串的值。无论如何,您的代码中也可能存在其他错误。使用调试器或 valgrind 检查。

顺便说一句,我不明白你为什么要strncpy在那里,因为你的源字符串和目标字符串的长度必须相同。为什么不strcpy改用?

于 2013-10-31T22:01:24.710 回答