2016-11-10 49 views
0

我使用一个结构来存储一个字符串,像这样的整数:如何添加项目到一个结构,而无需创建变量

struct movement { 
    char *direction; 
    int steps; 
}; 

我可以做这个

struct movement m1= { "right",20 }; 
struct movement m2= { "left" ,10 }; 
项目添加到结构

我试图达到的最终结果是收集用户输入(例如“右20”),并将其存储在结构中。如何在不使用变量(m1,m2等)的情况下将未知数量的用户输入存储到结构中,因为我不知道最后会有多少项。

+0

A [链表(http://www.thegeekstuff.com/2012/08/c-linked-list-例如/)可以提供帮助 –

+0

请注意,上面以任何方式执行* not *“将项目添加到结构中”。您正在创建两个独立的结构实例,彼此之间不需要做任何事情。 – usr2564301

+0

一组结构? – RoadRunner

回答

1

使用链接列表。这是一个递归的数据结构,对于你想要的是很好的。

下面是一些示例代码,我写了,而以前,这可能有助于:

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

/* basic linked list structure */ 
typedef struct node node_t; 

struct node { 
    char *direction; 
    int steps; 
    node_t *next; 
}; 

/* pointers to the head and tail of the list */ 
typedef struct { 
    node_t *head; 
    node_t *foot; 
} list_t; 

list_t *initialize_list(void); 
list_t *insert_nodes(list_t *list, char *direction, int steps); 
void free_list(list_t *list); 
node_t *generate_node(void); 
void print_list(list_t *list); 
void exit_if_null(void *ptr, const char *msg); 

int 
main(int argc, char const *argv[]) { 
    list_t *list; 

    /* empty list created */ 
    list = initialize_list(); 

    /* inserting information one a time */ 
    list = insert_nodes(list, "right", 20); 
    list = insert_nodes(list, "left", 10); 

    print_list(list); 

    /* freeing list at the end */ 
    free_list(list); 
    list = NULL; 

    return 0; 
} 

/* function to insert information into a node */ 
list_t 
*insert_nodes(list_t *list, char *direction, int steps) { 

    /* called generate_node() to create a new node */ 
    node_t *new; 
    new = generate_node(); 

    /* puts steps information into node */ 
    new->steps = steps; 

    /* allocates space for direction string */ 
    /* this is needed because *direction is a pointer */ 
    new->direction = malloc(strlen(direction)+1); 

    /* copies direction info into node */ 
    strcpy(new->direction, direction); 

    /* inserting information at the tail of the list */ 
    new->next = NULL; 

    if (list->foot == NULL) { 
     /* first insertion into list */ 
     list->head = list->foot = new; 
    } else { 
     list->foot->next = new; 
     list->foot = new; 
    } 

    /* returns modified list */ 
    return list; 
} 

.* function which generates new nodes */ 
node_t 
*generate_node(void) { 
    node_t *newnode; 

    /* create space for new node */ 
    newnode = malloc(sizeof(*newnode)); 
    exit_if_null(newnode, "Allocation"); 

    /* initialize node info to nothing */ 
    newnode->direction = NULL; 
    newnode->steps = 0; 

    return newnode; 
} 

/* creates the empty linked list */ 
list_t 
*initialize_list(void) { 
    list_t *list; 

    create space for list */ 
    list = malloc(sizeof(*list)); 
    exit_if_null(list, "Allocation"); 

    /* set pointers to NULL */ 
    /* We don't want them pointing at anything yet */ 
    list->head = list->foot = NULL; 

    return list; 
} 

/* function which prints entire list */ 
void 
print_list(list_t *list) { 

    /* start at the head of the list */ 
    node_t *curr = list->head; 

    while (curr) { 
     printf("%s %d\n", curr->direction, curr->steps); 

     /* steps through the list */ 
     curr = curr->next; 
    } 
} 

/* function which frees nodes */ 
void 
free_list(list_t *list) { 
    node_t *curr, *prev; 

    /* start at beginning of list */ 
    curr = list->head; 

    /* frees nodes one at a time */ 
    while(curr) { 
     prev = curr; 
     curr = curr->next; 
     free(prev); 
    } 

    /* frees entire list */ 
    free(list); 
} 

/* function which checks malloc(), and whether enough space was allocated */ 
void 
exit_if_null(void *ptr, const char *msg) { 
    if (!ptr) { 
     printf("Unexpected null pointer: %s\n", msg); 
     exit(EXIT_FAILURE); 
    } 
} 
+0

@Ryan Chia,这个代码有点帮助吗?如果你愿意,我可以更详细地解释它。 – RoadRunner

+0

非常感谢!我对C很陌生,所以解释会大大有助于:) –

+0

是啊没问题@RyanChia。我会在代码中添加注释,并且我还建议在互联网上查看它们。当想要将结构对象信息结合在一起时,它们是非常有用的数据结构。 – RoadRunner

-1

使用LinkedList存储不确定数量的移动。 对于每个移动,在链接列表中创建一个节点并更新下一个指针。

struct node { 
    struct movement m; 
    node* next; 
} 
3

它听起来并不像你真的想将值存储到结构中,而是想存储一系列独立的结构实例;每个用户输入一个。

三个这样做的最基本的方法是:

  • 的数组,其大小在编译时进行选择。它不应该太硬,使之“足够大”的合理的输入
  • 一个数组,其大小设置(然后增长)在运行时
  • 结构实例的链表

哪一个更喜欢取决于你认为哪一个最简单。如果可能的话,静态附件总是最简单的。你可以在全球范围内容易地拥有类似于

struct movement movements[10000]; 

这只在64位系统上花费大约120KB。请注意,这不包括direction字符串的内存;如果这些总是从“右”和“左”(也许是“向上” /“向下”太)选择,你可以代表它作为一个枚举,而不是:

enum direction { DIRECTION_LEFT = 0, DIRECTION_RIGHT, DIRECTION_UP, DIRECTION_DOWN }; 

这将使结构“自足“和(在64位系统上)较小,因为枚举将小于指针。

动态增长使用realloc()是不是太硬的数组,你可以看看,最多很容易为经常使用。

+0

我结束了使用完全不同的方法,并没有使用结构来实现我想实现的目标。不过,我仍然有兴趣尝试一个链接列表。我尝试在网上查找,但只发现“使用结构链接列表”而不是“结构链接列表”。我试图围绕努力让他们使用结构进行调整,但没有取得进展。你能为我指出正确的方向吗? –

+0

@RyanChia这听起来很像是一回事; C中的链表几乎总是用结构体来实现的,这是自然而然地实现它的方式。存储在每个元素中的东西可以是指针(无论你想要的)还是应用程序定义的结构。 – unwind

相关问题