在 class 中定义私有结构时,如何将其用作函数参数或 return 类型?

when defining a private structure in a class how do i use it as a function parameter or return type?

我创建了 graph.h、graph.cpp 和 main.cpp 在我的 graphics.h 中,我创建了两个私有结构一个 Edge 和一个节点,我首先在节点上方声明了 Edge,但是 Edge 有一个节点成员,所以我已经转发声明了 Node 结构 但我 运行 遇到了 "Graph::Node*" 不兼容的问题 "Node *" 这发生在我的 graph.cpp AddEdgeByName(string,string,double) 函数,为什么会这样?除此之外,我不知道为什么我必须在 (graphics.cpp) 中声明函数 Graph::Node * Graph::findByName(string name) 就像我认为我最初尝试声明它的方式一样这个 Node * Graph::findByName(string name) 可以工作,但它给了我一个错误。 我想顺便制作一个有向加权图。

#include <iostream>
#include <string>
#include <vector>



using std::cout;
using std::cin;
using std::endl;
using std::string;
using std::vector;

struct Node;

class Graph{

    private:
        typedef struct edge{
            double edgeWeight;
            Node *pointsTo;

            edge(){}
            edge(const edge & copyObject){
                this->edgeWeight = copyObject.edgeWeight;
                this->pointsTo = copyObject.pointsTo;
            }

        } Edge;

        typedef struct node{
            string name;
            vector<Edge> myEdges;// list of outgoing edges for this node

            node(string myName){
                name = myName;
            }

            node(const node & copyObject){
                this->name = copyObject.name;
                this->myEdges = copyObject.myEdges;
            }
            // adds another edge to this node
            void addEdge(Node *pointTo, double weight){
                Edge newEdge;
                newEdge.edgeWeight = weight;
                newEdge.pointsTo = 
                newEdge.pointsTo = pointTo;
                myEdges.push_back(newEdge);
            }
        } Node;

        vector<Node*> graph; // vector containing all the nodes for the
                             //graph
    public:
        Graph();
        // finds a node in the list of nodes for the graph, using the name
        Node * findByName(string name);

        void add(string name);

        void addEdgeByName(string first, string second,double weight);


};

#endif




// this is graphics.cpp

#include "Graph.h"


Graph::Graph(){



}

Graph::Node * Graph::findByName(string name){



    for(std::vector<Node*>::iterator it = graph.begin(); it != graph.end(); ++it){

        if((*it)->name == name){
            return *it;
        }
    }
    return NULL;
}

void Graph::add(string name){

    Node * newNode = new Node(name); // creates a new node with the given                 //name
    graph.push_back(newNode); // adds this node to our list of nodes in the //graph
}

// this publicly accessible function adds edges to each of the strings

void Graph::addEdgeByName(string first, string second,double weight){

    Node * firstNode = findByName(first);
    Node * secondNode = findByName(second);
    firstNode->addEdge(secondNode,weight);
    secondNode->addEdge(firstNode,weight);

}

不要在 C++ 中使用 typedef struct node { … } Node。那就是C.

NodeGraph 内部的一个结构,因此您需要在那里而不是外部声明它:

class Graph {
private:
    struct Node;

    struct Edge {
        …
    };

    struct Node {
        …
    };
};

关于public/private问题:你不能。具有 private 可见性的结构意味着它只能在您的代码函数中使用。

使其成为 public 将是一种解决方案。另一种选择是根本不使用嵌套 类。 (我个人不喜欢他们)。


你应该避免做 typedef struct edge {....} Edge; 。而是使用 struct Edge { .... }; 。给你的结构两个名字没有任何好处。

您的前向声明 struct Node; 声明了与 Graph::Node 不同的结构。也许您的意思是 struct Node; 位于 Graph 定义内。那么它将是 Graph::Node.

的前向声明

最后,Graph::Node * Graph::findByName(string name) 中需要 Graph:: 因为编译器是从左到右读取的,所以如果它看到 Node * 那么它还不知道你在说什么.使用 C++11 return 类型语法可以避免这个问题:

auto Graph::findByName(string name) -> Node *

-> 部分中的名称在 Graph 范围内查找,因为编译器已经看到我们正在实现一个 Graph 成员函数。