如何解决“<name>没有参数取决于模板参数”?</name>

时间:2013-11-25 20:02:44

标签: android c++ android-ndk

我正在将我的旧版VC ++项目转换为与Android NDK兼容,我遇到了一个奇怪的错误。消息说:

[armeabi] Compile++ thumb: procalc-core <= pcc_arithmetics.cpp
In file included from D:/Dokumenty/Dev/Android/ProCalc//jni/pcc_arithmetics.h:10:0,
                 from D:/Dokumenty/Dev/Android/ProCalc//jni/pcc_arithmetics.cpp:1:
D:/Dokumenty/Dev/Android/ProCalc//jni/pcc_common.h: In static member function 
'static std::string ProCalcCore::CommonTools::ToStringBase(T, int)':

D:/Dokumenty/Dev/Android/ProCalc//jni/pcc_common.h:102:68: error: there are no 
arguments to 'ConvertException' that depend on a template parameter, so a 
declaration of 'ConvertException' must be available [-fpermissive]

throw ConvertException(PROCALC_ERROR_SYNTAX_INVALID_INTEGER_BASE);
                                                                ^
D:/Dokumenty/Dev/Android/ProCalc//jni/pcc_common.h:102:68: note: (if you use 
'-fpermissive', G++ will accept your code, but allowing the use of an undeclared 
name is deprecated)

make.exe: *** [D:/Dokumenty/Dev/Android/ProCalc//obj/local/armeabi/objs/procalc-
core/pcc_arithmetics.o] Error 1

错误发生在以下地方:

template <typename T>
std::string CommonTools::ToStringBase(T val, int base)
{
    if (base < 2)
        throw ConvertException(PROCALC_ERROR_SYNTAX_INVALID_INTEGER_BASE);

命名大小的错误值是#define d int值。

ConvertException在另一个文件中声明:

namespace ProCalcCore
{
    (...)
    class ConvertException : public InternalException
    {
    public:
        ConvertException(const unsigned long int & newErrorCode);
    };

当我尝试将ConvertException更改为ProCalcCore::ConvertException时,我收到了另一个错误:

D:/Dokumenty/Dev/Android/ProCalc//jni/pcc_common.h:102:10: error: 'ConvertException' 
is not a member of 'ProCalcCore'

正确解析所有依赖关系 - 在VS中项目编译没有问题。

我该如何解决?是什么导致了这个错误?

1 个答案:

答案 0 :(得分:1)

“在Visual Studio中,项目编译没有问题”是您的依赖关系正确的弱证据。

问题是ConvertException在宣布template时不可见。某些版本的Visual Studio仅尝试在template实例化时绑定此类“免费”类型和表达式,这在C ++标准下是不正确的。

所以你的编译器指出它无法解决ConvertException所指的类型。为了让它知道它所引用的类型,你需要在使用它之前转发声明它(它可能有它自己的问题),或者#include头文件。

如果您认为自己已#include,那么问题通常是包含ConvertException的标题文件最终#include CommonTools::ToStringBase。头文件保护(或#pragma once)然后消除无限循环。

令人讨厌的是,如何消除无限循环取决于您首先包含哪个头文件!如果您包含ConvertException标头文件,则其中包含ToStringBase,其中包含ConvertException。第二个#include "ConvertException.h"被头文件#define警卫消除。

如果您首先包含ToStringBase,则会包含ConvertException,其中包含ToStringBase,这会被标头警卫消除。

所以包含的头文件首先被解析 second