简体   繁体   English

可以访问继承结构的结构

[英]Struct with access to inherited struct

I'm trying to write some functions to work on a balanced binary tree.我正在尝试编写一些函数来处理平衡二叉树。

First I wrote a typical binary tree interface.首先我写了一个典型的二叉树接口。 This encapsulates the general functionality associated with binary trees.这封装了与二叉树相关的一般功能。

The tree has nodes树有节点

typedef struct Node
{
  Node* left;
  Node* right;
  Node* parent;

  int key;

  void* value;

} Node;

and some functions that do insert , remove and search .以及一些insertremovesearch函数。

Now I want to extend that interface to work on a different types of binary trees, which inherits Node .现在我想扩展该接口以处理不同类型的二叉树,它继承了Node

typedef enum Color
{
  RED,
  BLACK

} Color;

typedef struct RBTreeNode
{
  Node* genericNode;
  Color color;

} RBTreeNode;

RBTree refers to Red-Black Trees RBTree指的是红黑树

The trouble ensues when I try to write a "tree repair" function.当我尝试编写“树修复”功能时,麻烦接踵而至。

void repairRBTree(Node* nodeInserted)
{

  // If nodeInserted's parent is NULL, nodeInserted is the root of the tree.
  // Red-Black tree properties suggest root node's color be black.
  if (nodeInserted->parent == NULL)
    {
      RBTreeNode* nodeInsertedTC = (RBTreeNode*)nodeInserted;
      nodeInsertedTC->color      = BLACK;
    }

  // If nodeInserted's parent's color is BLACK, nodeInserted has replaced a RED NULL node.
  // Red-Black tree properties suggest RED node's parent be BLACK,
  // which is the case currently, so there's nothing to be done.
  else if (nodeInserted->parent->(COLOR??))
    {
      return;
    }
}

In this if statement,在这个if语句中,

  if (nodeInserted->parent == NULL)
    {
      RBTreeNode* nodeInsertedTC = (RBTreeNode*)nodeInserted;
      nodeInsertedTC->color      = BLACK;
    }

if I had previously cast nodeInserted as Node* , that means the pointer itself is a RBTreeNode* , so if what I'm thinking is correct, casting it back to RBTreeNode* should do what I think it should.如果我之前将nodeInsertedNode* ,这意味着指针本身是一个RBTreeNode* ,所以如果我的想法是正确的,将它转换回RBTreeNode*应该做我认为应该做的事情。

But here但在这里

  // If nodeInserted's parent's color is BLACK, nodeInserted has replaced a RED NULL node.
  // Red-Black tree properties suggest RED node's parent be BLACK,
  // which is the case currently, so there's nothing to be done.
  else if (nodeInserted->parent->(COLOR??))
    {
      return;
    }
}

I don't have access to nodeInserted->parent 's Color enum.我无权访问nodeInserted->parentColor枚举。 And I don't think casting it to RBTreeNode will do much good.而且我认为将其转换为RBTreeNode不会有多大好处。

The only solution I know will work is if I rewrite all of my generalized functions to take in RBTreeNode as param instead of Node , but I really don't want to do that.我知道唯一可行的解​​决方案是,如果我重写所有通用函数以将RBTreeNode作为参数而不是Node ,但我真的不想这样做。

Is there a better solution?有更好的解决方案吗?

You should not use a pointer to implement inheritance.您不应该使用指针来实现继承。 Use a Node field instead of a pointer:使用Node字段而不是指针:

typedef struct RBTreeNode
{
  Node genericNode;
  Color color;

} RBTreeNode;

This way, when you cast Node* to RBTreeNode* , it will have access to all the fields of RBTreeNode .这样,当您将Node*RBTreeNode* ,它将可以访问RBTreeNode所有字段。

Since you are probably using a c++ compiler, a c++ analogy might help.由于您可能使用的是 c++ 编译器,因此 c++ 类比可能会有所帮助。 Having a first field of type Node is like having inheritance in c++, ie struct RBTreeNode: Node .拥有Node类型的第一个字段就像在 C++ 中拥有继承一样,即struct RBTreeNode: Node Having a first field of a pointer type is like having virtual inheritance, ie struct RBTreeNode: virtual Node .拥有指针类型的第一个字段就像拥有虚拟继承,即struct RBTreeNode: virtual Node Both ways work, until you need a downcast.两种方式都有效,直到您需要沮丧。 Virtual inheritance in c++ alerts the reader that you have something fishy about your inheritance hierarchy ("diamond inheritance"), so you should only use it when normal inheritance won't do. C++ 中的虚拟继承提醒读者你的继承层次结构(“钻石继承”)有些可疑,所以你应该只在正常继承不起作用时使用它。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM