为什么打印简单链接列表的代码不起作用?

时间:2018-04-09 18:48:46

标签: c++ data-structures structure

#include <iostream>
using namespace std;

typedef struct NODE node;

typedef struct NODE {
  int marks;
  char name[100];
  node *next;
} node;

node *getinput() {
  node *n;
  n = (node *)malloc(sizeof(node));
  if (n) {
    cin >> n->marks; // STATEMENT 1
    gets_s(n->name);
    n->next = NULL;
  }
  return n;
}

node *populateList(node *list) {
  node *temp;
  node *newptr = getinput();
  if (list == NULL) {
    list = newptr;
    return list;
  }

  temp = list;
  while (temp->next) {
    temp = temp->next;

    //(COMMENT 1)temp->next = newptr;
  }

  temp->next = newptr;
  return list;
}

void printlist(node *list) {
  node *p = list;

  // temp = list;
  while (p->next) {
    cout << p->marks << endl; // STATEMENT 2

    //(COMMENT 3) cout << list->marks << endl;

    puts(p->name);
    p = p->next;
  }
}

void main() {
  int x = 1;
  node *n = NULL;

  for (; x <= 6; x++)
    n = populateList(n);

  printlist(n);
}

所以,我面临一些问题:

  1. 我无法取得6个成员所需的标记和名称,而是我可以取6个成员的名字,但不能取其标记。 (如果我删除STATEMENT 1 AND / OR STATEMENT 2,则显示相同的输出)。

  2. 我假设成员的标记被视为链表的指针 node * list 的垃圾值,因为它似乎对所有成员都是相同的。< / p>

  3. 那么如何解决我的程序中的问题呢?我知道这个问题对许多人来说似乎太微不足道了,我可以很容易地在互联网上查找一个链接列表程序,但我决心让这个工作。我想知道代码中的其他问题/优化,以便我自己纠正。

    由于

2 个答案:

答案 0 :(得分:1)

您正在将C ++与C代码混合, 一些小修复程序。 使用std::string name代替char name[100] 使用n = new node()

最后为你&#34; bug&#34;您应该将gets_s(n->name);切换为cin >> (n->name); 这将起作用并填充标记和名称的正确值。 我很确定问题来自于使用C ++函数cin和C函数gets_s混合来自stdin的输入,其中看起来gets_s在调用第一个cin之后取值的分隔符。

也不要忘记删除已分配的节点。

答案 1 :(得分:0)

您的代码中存在多个问题;导致错误处理输入的是您将cingets_s混合,这通常不会按预期工作;顺便说一句:gets_sgets是#34;旧式C风格,在新标准中已被弃用(甚至删除)。例如,使用std::getline作为替代。

将积分值和字符串与白色空格混合起来实际上有点棘手。例如,如果输入为10 john doe,则cin >> marks将读入10,但会在输入缓冲区中留空;你必须跳过白色空格,例如cin >> ws;否则,您的字符串输入将立即终止或 - 如果使用getline - 在开头包含空格。然后,如果您编写string name; cin >> name,则只会读取john,因为字符串输入会以第一个空格停止。因此,我建议您使用getline阅读该名称,直到行尾,以便您真正得到john doe作为名称。

此外,请考虑输入可能失败(例如文件结束或格式无效),以致getinput可能必须返回无效节点(应由nullptr表示)。

很多事情,所以我重写了你的代码,以考虑上面提到的事情。希望能帮助到你;玩得开心!

struct node {
    int marks;
    string name;
    node *next;
};

node *getinput() {
    int marks;
    string name;
    if (! (cin >> marks >> std::ws)) {
        return nullptr;
    }
    if (! getline(cin, name, '\n')) {
        return nullptr;
    }
    return new node { marks, name, nullptr };
}

node *addToList(node *list, node* newNode) {
    if (list == NULL) {
        return newNode;
    }
    if (newNode == nullptr) {
        return list;
    }

    node* temp = list;
    while (temp->next) {
        temp = temp->next;
    }

    temp->next = newNode;
    return list;
}

void printlist(node *list) {
    node *p = list;
    while (p) {
        cout << p->marks << " " << p->name << endl;
        p = p->next;
    }
}

int main() {
    int x = 1;
    node *n = NULL;
    node *list = NULL;

    while (x <= 3 && (n = getinput()) != nullptr) {
        list = addToList(list, n);
        x++;
    }

    printlist(list);
}