创建链表的函数的函数类型

在写创建链表的函数时,有时需要让函数有返回值,有时不需要。忙活了半天找到两个比较有代表性的函数,希望帮忙看一下问题在哪。
这是第一个函数(指creatlist),函数类型为void,但可以通过print函数遍历输出。

#include <stdio.h>
#include <stdlib.h>
typedef struct  ListNode
{
    int data;
    struct listnode *next;
    /* data */
}listnode;
void creatlist(listnode *list, int n);  //这里是尾接法,所以第一个head中的数值没有发生改变
void printlist(listnode *list);
// listnode *readlist();
int main()
{
    int n;
    printf("请输入链表大小\n");
    scanf("%d", &n);
    // listnode *list = readlist();
    listnode *list = (listnode*)malloc(sizeof(listnode));
    creatlist(list, n);
    printlist(list);
}
void creatlist(listnode *list, int n){
    listnode *head, *node, *end;
    head = list;
    end = head;
    printf("请输入%d个数\n",n);
    int i;
    for(i = 0; i < n; i++){
        node = (listnode*)malloc(sizeof(listnode));
        scanf("%d", &node->data);
        end->next = node;
        end = node;
    }
    end->next= NULL;
}/*this is right*/
void printlist(listnode *list){
    listnode *p;
    p = list->next;
    while(p!= NULL){
        printf("%d ", p->data);
        p = p->next;
    }
}

这是第二个函数(指creatlist),若返回类型为void,debug时发现跳出函数后链表值没有发生改变,只有返回链表才能创建。

#include <stdio.h>
#include <stdlib.h>//使用malloc时必须有
typedef struct ListNode{
    int data;
    struct ListNode *next;
}listnode;
listnode */*void*/ creatlist(listnode *L);
void printlist(listnode *L);
int main()
{
    listnode *L = (listnode*)malloc(sizeof(listnode));//对要进行操作的指针必须先赋值,若为初始则用malloc分配,若是辅助指针则用其他指针赋值
    L = creatlist(L);
    printlist(L);
}
listnode */*void*/ creatlist(listnode *L){
    listnode *head, *node, *end;
    head = NULL;//通过此步骤保证从头赋值
    printf("请输入一组以-1结尾的数\n");
    int data;
    while(1){
        scanf("%d", &data);
        if(data == -1) break;
        else{
            node = (listnode*)malloc(sizeof(listnode));//必须在循环中分配内存
            node->data = data;
            if(head == NULL) {
                head = node;
                end = head;
            }
            else end->next = node;
            end = node;
        }
    }
    end->next = NULL;//避免链表中最后某一层的next是野指针导致输出时错误
    L = head;
    return L;//必须有返回
}
void printlist(listnode *L){
    listnode *p = L;
    while(p){
        printf("%d ",p->data);
        p = p-> next;
    }
}

求帮忙

看来你对指针理解的不透彻
现在,我们把listnode *整体看成一个类型,就比如假设他是type吧,你的creatlist就成了

void creatlist(type list, int n)

你想做的是修改list的值,但这样能做到吗?比如说

void func(int a)
{
  a=5;
}

这样能修改a的值吗?显然不能,如果要修改的话,需要写成这样:

void func(int* a)
{
  *a=5;
}

然后调用的时候用func(&x);
同理,这里如果想修改list,需要用

void creatlist(type* list, int n)

也就是

void creatlist(listnode** list, int n)

其实这两种写法,没有区别,第二种写法函数返回也可以是 void ,关键是对第37行的修改,如下,供参考:

#include <stdio.h>
#include <stdlib.h>//使用malloc时必须有
typedef struct ListNode{
    int data;
    struct ListNode *next;
}listnode;
void creatlist(listnode *L);   //listnode *  修改
void printlist(listnode *L);
int main()
{
    listnode *L = (listnode*)malloc(sizeof(listnode));//对要进行操作的指针必须先赋值,若为初始则用malloc分配,若是辅助指针则用其他指针赋值
    creatlist(L);  // L =   修改
    printlist(L);
    
    return 0;
}
void creatlist(listnode *L){  //listnode *  修改
    listnode *head, *node, *end;
    head = NULL;//通过此步骤保证从头赋值
    printf("请输入一组以-1结尾的数\n");
    int data;
    while(1){
        scanf("%d", &data);
        if(data == -1) break;
        else{
            node = (listnode*)malloc(sizeof(listnode));//必须在循环中分配内存
            node->data = data;
            if(head == NULL) {
                head = node;
                end = head;
            }
            else end->next = node;
            end = node;
        }
    }
    end->next = NULL;//避免链表中最后某一层的next是野指针导致输出时错误
    L->next = head;  //L = head;   修改
    //return L;//必须有返回        修改
}
void printlist(listnode *L){
    listnode *p = L->next;      //修改
    while(p){
        printf("%d ",p->data);
        p = p-> next;
    }
}