【问题标题】:How to set up explicit value constructor with linked list?如何使用链表设置显式值构造函数?
【发布时间】:2012-06-10 20:33:47
【问题描述】:

对于一个项目,我试图设置一个链表对象,以便可以使用显式值构造函数对其进行初始化。我希望它看起来像这样:

WORD you("you");//where the object you's linked list now contains y o u;

但是当我打印出你的对象时,我看到的只是这个符号“=” 当我打印出你的长度时,我得到 -858993459

这是我的显式值构造函数,谁能告诉我我做错了什么?

WORD::WORD(string s)
{
front = 0;
int i = 0;
int len = s.length();

if(front == 0)
{   
    front = new alpha_numeric;
    alpha_numeric *p = front;

    while(s[i] <= len)
    {
        p -> symbol = s[i];
        p -> next = new alpha_numeric;
        p = p -> next;
        p -> symbol = s[i++];
    }
    p -> next = 0;
}
}

如果有帮助,这里是类声明文件

#include <iostream>
#include <string>

using namespace std;
#pragma once

class alpha_numeric //node
{
public:
char symbol; //data in node
alpha_numeric *next;//points to next node
};

class WORD
{
public:
WORD(); //front of list initially set to Null
WORD(const WORD& other);
WORD(string s); //***EXPLICIT VALUE CONSTRUCTOR
bool IsEmpty(); //done
int Length();
void Add(char); //done
//void Insert(WORD bword, int position);
//void operator=(char *s);

friend ostream & operator<<(ostream & out, const WORD& w);//done

private:
alpha_numeric *front; //points to the front node of a list
int length;
};

【问题讨论】:

  • 我认为您要查找的术语是conversion constructor。显式构造函数有 explicit 关键字,不能像你的那样进行隐式转换。
  • 我会先从你的标题中删除using namespace std;。与#include &lt;iostream&gt; 相同,在声明类时不需要包含它 - 将其移至处理流的 .cpp。
  • 还有front = 0;if(front == 0) 紧随其后。干什么用的?
  • 你为什么不直接委托给你自己的Add() 方法呢?干燥。
  • 对。为什么不能从构造函数本身调用Add()

标签: c++ linked-list explicit-constructor


【解决方案1】:

您的 while 循环不太可能正在执行。我相信:

while(s[i] &lt;= len)

应该是

while(i &lt; len)

【讨论】:

    【解决方案2】:

    您已将 std::string sint i 初始化为 0。然后你将 int len 初始化为 s.length(); 并且你想遍历这个字符串:

    while(s[i] <= len) <----------------- THIS IS WRONG
    {
        ...
        p -> symbol = s[i++];
    }
    

    另请注意,std::basic_string::length() 的复杂度为 O(1)。使用临时变量len 毫无意义。您还做了很多多余的事情,例如将0 分配给front,然后检查if (front == 0)。它可能看起来像这样:

    WORD::WORD(std::string s)
    {
        length = s.length();
        if (length == 0)
        {
            front = NULL
            return;
        }
    
        front = new alpha_numeric;
        alpha_numeric *p = front;
    
        int i = 0;
        while(i < length - 1)
        {
            p->symbol = s[i++];
            p->next = new alpha_numeric;
            p = p->next;
        }
        p->symbol = s[i];
        p->next = NULL;
    }
    

    【讨论】:

    • 如果您决定使用这个,请不要忘记在丢弃参考之前删除最后一个 alpha_numeric。
    • 这行得通,现在唯一的问题是,它出现的是 y o u u,而不是 y o u。你知道为什么要添加这个额外的字符吗?
    • @nw.:感谢您指出内存泄漏。现在检查我的答案。
    • @MikeGordon:我已经更新了我的答案。不过我有一个问题要问你:你确定没有人会尝试打电话给WORD("") 吗?
    • @LihO 好的,我明白了,不,我不确定没有人会尝试。
    【解决方案3】:

    你从不设置长度,这就是为什么它是垃圾。正如 luthien256 ahd LihO 指出的那样,您的 while 循环也是错误的,并且 if (front == 0) 测试没有意义。

    最后,不需要p -&gt; symbol = s[i++];。只需增加 i。

    试试这个:

    class alpha_numeric //node
    {
    public:
    char symbol; //data in node
    alpha_numeric *next;//points to next node
    };
    
    class WORD
    {
    public:
    WORD(); //front of list initially set to Null
    WORD(const WORD& other);
    WORD(string s); //***EXPLICIT VALUE CONSTRUCTOR
    bool IsEmpty(); //done
    int Length() { return length; }
    alpha_numeric *Front() { return front; }
    void Add(char); //done
    //void Insert(WORD bword, int position);
    //void operator=(char *s);
    
    friend ostream & operator<<(ostream & out, const WORD& w);//done
    
    private:
    alpha_numeric *front; //points to the front node of a list
    int length;
    };
    
    WORD::WORD(string s)
    {
      front = 0;
      int i = 0;
      int len = s.length();
      length = len;
      if (length == 0) {
        front = NULL;
        return;
      }
      front = new alpha_numeric;
      alpha_numeric *p = front;
    
      while(i < len)
      {
          p -> symbol = s[i];
          if (i != len - 1) {
            p -> next = new alpha_numeric;
            p = p -> next;
          }
          else
            p -> next = NULL;
          ++i;
      }
    }
    
    
    int main() {
      WORD you("you");
      alpha_numeric* front = you.Front();
      while(front != NULL) {
        cout<<(front->symbol)<<endl;
        front = front->next;
      }
      cout<<you.Length()<<endl;
      return 0;
    }
    

    【讨论】:

    • @MikeGordon 在我看来不错。也许您的打印功能有错误?
    • @Mike Gorden - 我运行它时不会发生这种情况。我在上面包含了整个代码,以及示例 main() 方法。它打印 y o u,然后打印 3 作为长度。
    • @Mike Gorden - 另外,我添加了一个空字符串测试,所以如果你传入“”,那么它就会被处理。
    【解决方案4】:

    试试这个:

    WORD::WORD(string s)
    {
      int i;
      int len = s.length();
    
      front = new alpha_numeric;
      alpha_numeric *p = front;
    
      for(i = 0; i < len; i++)
      {
            p -> symbol = s[i];
            p -> next = (i == len - 1) ? 0 : new alpha_numeric;
            p = p -> next;
      }
    }
    

    【讨论】:

    • 其实,将0 赋值给p-&gt;next 最好在循环后离开。在您对条件i == len - 1 的代码评估中是多余的。
    • 如果不需要,最好不要分配next。
    猜你喜欢
    • 1970-01-01
    • 2021-07-20
    • 2017-03-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-02-20
    相关资源
    最近更新 更多