簡體   English   中英

C中字符串單鏈表的實現

[英]Implementation of a string singly linked list in C

我想在每個節點中創建一個包含字符串而不是整數的單鏈表。

但是,我無法實現它。 有人可以告訴我實施有什么問題嗎?

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

struct node {
  char data;
  struct node* next;
};

struct node* create(struct node* head, const char* data) {
  struct node* newnode, * temp;
  newnode = (struct node*)malloc(sizeof(struct node));
  newnode->data = data;
  newnode->next = NULL;
  if (head == NULL) {
    head = newnode;
    temp = newnode;
  }
  else {
    temp->next = newnode;
    temp = temp->next;
  }
  temp->next = NULL;
  return head;
}

struct node* display(struct node* head) {
  struct node* temp;
  temp = head;
  while (temp != NULL) {
    printf("%d->", temp->data);
    temp = temp->next;
  }
  printf("NULL");
  return head;
}

int main() {
  struct node* head;
  head = NULL;
  int size, i;
  char str[5];
  printf("\nSize of linked list you want: ");
  scanf("%d", &size);
  for (i = 0; i < size; i++) {
    gets(str);
    head = create(head, str);
  }
  display(head);
  return 0;
}

char data包含單個字符。 這不是你想要的,對吧? 你想保存一個字符串,即指向第一個字符的指針:

struct node {
  char *data;
  struct node* next;
};

這通過指針保存字符串 - 不清楚您是否希望此指針成為擁有指針(即如果節點消失,則字符串也會消失)或引用(即其他人擁有字符串並管理其生命周期) .

還有其他錯誤,但這是一個很好的起點。 並啟用來自編譯器的所有警告,並全部理解它們,因為如果你的代碼,它們中的大多數都是 C 語言允許的錯誤(因為它不能確定你真正想要什么) - 但那不是表示代碼正確。

保存字符串的另一種方法可能是按值,即,您可以保存一個數組,而不是像您在答案中所做的那樣只包含一個字符 -請參閱此問題的另一個答案以了解如何做到這一點 通過指針擁有字符串還是將其作為值擁有之間的選擇在介紹性教學代碼中並不重要,因為您不會在實際用例中測量數據結構的性能。 所以沒有“一個真正的選擇”:每一個在某些用例中都有好處。

一些含糊的建議(總是要經過測量:)可能是:

  • 如果值是恆定的,那么按值將字符串保持為固定大小或可變大小通常會在性能上獲勝

  • 如果值的大小范圍很小(例如,所有字符串都是“短”),則具有固定大小的節點並將其分配到連續的 memory 池中可能會提高性能

  • 如果值發生變化,那么按值保存字符串並不總是可行的:可能需要重新分配節點以調整其大小,然后您需要一個雙向鏈表來調整相鄰節點的指針以反映新地址節點

  • 最通用且可能性能最差的選項是通過擁有指針保存字符串,因此節點可以保持在固定地址,但字符串可以移動; 在這種情況下,如果有很多小字符串,則小字符串優化可能會進一步改進:將字符串保存在節點的固定大小 char 數組中(如果它適合),否則將其分配在單獨的 memory 塊中; 這就是在std::string的實現中通常會做的事情,它可以提高性能。 想法是,由於字符串是“大”的,因此與使用該字符串的實際值所做的任何工作相比,必須引用其他地址來獲取其數據的開銷將是微不足道的。

有幾個問題:

  • 您的結構中需要一個char數組,而不是 c char
  • create function 過於復雜和錯誤

OTOH 你的display function 是正確的。

你要這個:

有關解釋,請查看評論。

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

#define MAXSTRINGSIZE 100                  // maximum allowed size of strings

struct node {
  char data[MAXSTRINGSIZE];                // we need an array of char her, not a char
  struct node* next;
};

struct node* create(struct node* head, const char* data) {
  struct node* newnode = malloc(sizeof(struct node));   // no cast is needed with malloc
  strcpy(newnode->data, data);             // copy the string

  newnode->next = head;  
  return newnode;
}

struct node* display(struct node* head) {
  struct node* temp;
  temp = head;
  while (temp != NULL) {
    printf("%s->", temp->data);
    temp = temp->next;
  }

  printf("NULL");
  return head;
}

int main() {
  struct node* head;
  head = NULL;
  int size;
  char str[MAXSTRINGSIZE];
  printf("\nSize of linked list you want: ");
  scanf("%d", &size);

  getchar();             // absorb \n, scanf and gets don't mix well

  for (int i = 0; i < size; i++) {
    gets(str);
    head = create(head, str);
  }

  display(head);
  return 0;
}

筆記

  • 您可以使用指針並僅分配存儲字符串所需的 memory 數量,而不是在結構中使用固定大小的data成員。 我讓你自己解決這個問題。
  • 而不是gets是已棄用的 function,您應該使用fgets 閱讀內容以獲取更多信息。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM