【问题标题】:Cannot recognise the typedef type defined in .h file无法识别 .h 文件中定义的 typedef 类型
【发布时间】:2016-09-12 07:04:08
【问题描述】:

我在让编译器识别 .tem 文件(用于将实现与 .h 文件分开)中的函数模板的返回类型时遇到问题。

In file included from tests/Graph.h:57:0,
                 from tests/test1.cpp:3:
tests/Graph.tem:28:2: error: ‘reference’ does not name a type
  reference Node_Iterator<N, E>::operator*() const {
  ^~~~~~~~~
tests/Graph.tem:33:2: error: ‘pointer’ does not name a type
  pointer Node_Iterator<N, E>::operator->() const {

不知道我做错了什么。我使用typedef 来定义返回类型的类型。

/* 
 * File: Graph.h
 */

#ifndef _Graph_h
#define _Graph_h

#include <vector>
#include <algorithm>
#include <string>
#include <memory>
#include <iostream>
#include <exception>
#include <map>
#include <set>
#include <typeinfo>

namespace gdwg {

    template <typename N, typename E> class Graph; // function prototype for Graph class

//-----------------------------------------------------------
// Iterators for Graph with Nodes N and Edges E
//-----------------------------------------------------------

    // Iterator class for Node N
    template <typename N, typename E> class Node_Iterator {

    public:
            typedef typename Graph<N, E>::Node Node;

            typedef std::ptrdiff_t                     difference_type;
            typedef std::forward_iterator_tag          iterator_category;
            const typedef N                            value_type;
            const typedef N*                           pointer;
            const typedef N&                           reference;

            // operators for value and reference types
            reference operator*() const;
            pointer operator->() const;



    private:
            bool end;
            typename std::vector< std::shared_ptr<Node> >::iterator it;
            typename std::vector< std::shared_ptr<Node> > mynodes_;

    };


    #include "Graph.tem" // definition/implementation of Graph, Node_Iterator and Edge_Iterator classes

}

#endif

这是 .tem 文件,它是 Graph.h 文件的实现,我将其包含在 .h 文件的底部。

#include <vector>
#include <algorithm>
#include <string>
#include <memory>
#include <iostream>
#include <exception>
#include <map>
#include <set>
#include <typeinfo>

namespace gdwg {

    //-----------------------------------------------------------
    // Implementation of Iterator class for Node N
    //-----------------------------------------------------------

    // operators for value and reference types
    template <typename N, typename E> 
    reference Node_Iterator<N, E>::operator*() const {
        return (*it)->val_;
    }

    template <typename N, typename E> 
    pointer Node_Iterator<N, E>::operator->() const {
        return &(operator*());
    }




}

【问题讨论】:

    标签: c++ templates operators typedef typename


    【解决方案1】:
    1. 为它们添加限定名称(使用typename 关键字,参见Where and why do I have to put the “template” and “typename” keywords?),例如:

      typename Node_Iterator&lt;N, E&gt;::reference ...
      typename Node_Iterator&lt;N, E&gt;::pointer...

    2. Graph.h中,#include "Graph.tem"在命名空间gdwg的定义中,而在Graph.tem中,函数定义在另一个命名空间gdwg中,然后它们将在命名空间中定义gdwg::gdwg。您可以将#include "Graph.tem" 移出Graph.h 中的命名空间定义,或删除Graph.tem 中的命名空间定义。

    【讨论】:

    • 根据我的规格,它应该在里面。好的,错误消失了,但我得到了这个:tests/Graph.tem:28:75: error: definition of 'const N& gdwg::Node_Iterator::operator*() const' is not in namespace enclosing' gdwg::Node_Iterator' [-fpermissive] 类型名 Node_Iterator::reference Node_Iterator::operator*() const {
    • @iteong 这就是问题所在。 #include "Graph.tem"在命名空间gdwg的定义里面,在Graph.tem里面又定义了另一个命名空间gdwg,最后变成namespace gdwg { namespace gdwg { ...这样的东西。如果你必须在命名空间定义里面#include "Graph.tem",那么删除Graph.tem中的命名空间定义。
    • 哦,好吧,我要删除 .tem 文件中的 gdwg 吗?
    • @iteong 是的,应该没问题。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-05-20
    • 2023-03-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-13
    • 2017-11-30
    相关资源
    最近更新 更多