-2

所以我有一个具有多个节点的前缀树对象。每个节点都由一个字符组成,无论它是最终节点,还是存储在对象指针数组中的子节点(最多 26 个值)。我需要打印在给定节点下找到的单词。

下面的例子。

 a
/ \
b  c
    \
     t

如果在带有字符“a”的节点上调用该函数,它应该打印 ab 并采取行动。我计划通过添加到一个字符串直到到达一个标记为 final 的节点然后删除该字母来做到这一点。我想实现一个递归函数,但是在将一个节点设置为该节点的子节点时,我遇到了分段错误。

void PrefixTreeNode::printAllWords() const
{
  PrefixTreeNode* node; 

  for(char i = 'a'; i < 'a' + ALPHABET_SIZE; i++)
  {
    if(getChild(i) != nullptr)
    {
      if(!isFinal())
      {
        nodeList.push_back(i);
        cout << "added: " << i << endl;
        node = node->getChild(i);    //this line results to segmentation fault
        node->printAllWords();       //How would I call the function on the node's child?
      }
      else if(isFinal()) 
      {
        nodeList.push_back(i);
        cout << nodeList;
        nodeList.pop_back();
        return;
      }
    }
  }
}

获取子函数:

PrefixTreeNode* PrefixTreeNode::getChild(char c)
{
  if (isalpha(c))
    return link[tolower(c)-'a'];
  else
    return nullptr;
}

const PrefixTreeNode* PrefixTreeNode::getChild(char c) const
{
  if (isalpha(c))
    return link[tolower(c)-'a'];
  else
    return nullptr;
}

节点对象:

class PrefixTreeNode
{
  friend PrefixTree;
private:
  char c;
  bool final;
  PrefixTreeNode* link[ALPHABET_SIZE];
public:
  //Constructs a new node
  PrefixTreeNode();
  //Copy constructor
  PrefixTreeNode(const PrefixTreeNode&);
  //Copy assignment
  const PrefixTreeNode& operator=(const PrefixTreeNode&);
  //Returns the character this node contains
  char getChar() const { return c; }
  //Returns whether this node is the end of a word
  bool isFinal() const { return final; }
  //Changes whether this node is the end of a word
  void setFinal(bool b) { final = b; }
  //Returns the node corresponding to the given character
  PrefixTreeNode* getChild(char);
  //Returns the node corresponding to the given character
  const PrefixTreeNode* getChild(char) const;
  //Adds a child corresponding to the given character
  void addChild(char);
  //Removes the child corresponding to the given character
  void deleteChild(char);
  //TODO:  print all words that end at or below this PrefixTreeNode
  void printAllWords() const;
  //Destructor
  ~PrefixTreeNode();
};
4

1 回答 1

0

如果我只是告诉你为什么线路是由段错误引起的,我可以说你可以初始化变量节点,在线路上方。

我不知道整个代码,但我建议将其更改为这样。

void PrefixTreeNode::printAllWords() const
{
  for(char i = 'a'; i < 'a' + ALPHABET_SIZE; i++)
  {
    PrefixTreeNode* node = getChild(i); 
    //if(getChild(i) != nullptr)
    if(node != nullptr)
    {
      nodeList.push_back(i);//this line will be run, ALWAYS whatever the return of isFinal, so I moved it to here.
      if(!isFinal())
      {
        //nodeList.push_back(i); //moved to the front of 'if'
        cout << "added: " << i << endl;
        //just remove it
        //node = node->getChild(i);    //this line results to segmentation fault
        node->printAllWords();       //How would I call the function on the node's child?
      }
      //else if(isFinal()) //duplicated
      else
      {
        //nodeList.push_back(i); //moved to the front of 'if'
        cout << nodeList; //I don't know the type of nodeList, but you may take care of it.
        nodeList.pop_back();
        return;
      }
    }
  }
}

于 2019-10-24T03:09:14.923 回答