c++ - 错误:没有匹配的函数调用'function namel'
问题描述
我的最终目标是计算二次理想的幂,它使用 GMP 库在 C 中作为结构变量实现。
我得到了一个库(ANTL),其中包含使用 C++ 模板、命名空间和 NTL 的通用优化指数。该库对 NTL 类型 ZZ_p 等和基本类型(如 long、float 等)进行求幂。
我必须使用 ANTL 库来实现我的最终目标——计算理想的能力,即C 结构变量。因为在我想实现基本 mpz_t 变量的强大功能之前,我从未使用过模板和命名空间,以了解一切是如何工作的。
现在,我有四个头文件 exp.hpp、expbin.hpp、impl.hpp、com.hpp 和一个主文件 exp.cpp,如下所示 -
COM.HPP
#ifndef GMPL_COM_H
#define GMPL_COM_H
#include <gmp.h>
namespace GMPL {
template < class T >
inline void assign(T C, const T A)
{
mpz_set(C, A);
}
template<class T>
void mul (T C, const T A, const T B)
{
mpz_mul(C, A, B);
}
template<class T>
void sqr (T C, const T A)
{
mpz_mul(C, A, A);
}
}
#endif // guard
EXP.HPP
#ifndef EXP_H
#define EXP_H
#include "com.hpp"
namespace GMPL
{
template < class T >
class exp
{
public:
exp() {};
virtual ~exp() {};
virtual void power (T C, const T A, const NTL::ZZ & n) = 0;
};
} // GMPL
#endif // EXP_H
EXPBIN.HPP
#ifndef EXPBIN_H
#define EXPBIN_H
#include "exp.hpp"
namespace GMPL
{
template < class T >
class expbin : public exp<T>
{
public:
expbin() {};
~expbin() {};
void power (T C, const T A, const NTL::ZZ & n);
};
} // GMPL
// Unspecialized template definitions.
#include "impl.hpp"
#endif // EXPBIN_H
执行HPP
using namespace GMPL;
//
// compute A^n using standard left-to-right binary method
//
template < class T >
void expbin<T>::power (T C, const T A, const NTL::ZZ & n)
{
assign(C,A);
for (register long i = NumBits(n)-2 ; i >= 0 ; i--)
{
sqr(C, C);
if (bit(n, i) == 1)
mul(C, C, A);
}
}
EXP.CPP
#include <NTL/lzz_p.h>
#include <gmp.h>
namespace GMPL {}
using namespace GMPL;
#include "expbin.hpp"
NTL_CLIENT
int main ()
{
// NTL variables
ZZ n;
// GMP variables
mpz_t aa;
mpz_t bb;
mpz_init(aa);
mpz_init(bb);
// generate random exponent of size 512 bits
RandomLen (n, 512); // NTL function
// initialize exponentiation classes
expbin<mpz_t> obj;
// compute a^n with available methods
obj.power (bb,aa,n);
// check and output results
gmp_printf("%Zd", bb);
}
当我尝试使用(如 Victor Shoup 的在线 NTL 文档中所述)编译EXP.CPP时
g++ -g -O2 -std=c++11 -pthread -march=native exp.cpp -o t -lntl -lgmp -lm
我收到以下错误消息-
$ g++ -g -O2 -std=c++11 -pthread -march=native exp.cpp -o t -lntl -lgmp -lm
In file included from exp.cpp:8:
In file included from ./expbin.hpp:46:
./impl.hpp:16:10: warning: 'register' storage class specifier is deprecated and
incompatible with C++1z [-Wdeprecated-register]
for (register long i = NumBits(n)-2 ; i >= 0 ; i--)
^~~~~~~~~
./impl.hpp:15:5: error: no matching function for call to 'assign'
assign(C,A);
^~~~~~
exp.cpp:28:9: note: in instantiation of member function
'GMPL::expbin<__mpz_struct [1]>::power' requested here
obj.power (bb,aa,n);
^
./com.hpp:16:17: note: candidate template ignored: deduced conflicting types for
parameter 'T' ('__mpz_struct *' vs. 'const __mpz_struct *')
inline void assign(T C, const T A)
^
In file included from exp.cpp:8:
In file included from ./expbin.hpp:46:
./impl.hpp:20:13: error: no matching function for call to 'mul'
mul(C, C, A);
^~~
./com.hpp:22:10: note: candidate template ignored: deduced conflicting types for
parameter 'T' ('__mpz_struct *' vs. 'const __mpz_struct *')
void mul (T C, const T A, const T B)
对这些错误的刻苦谷歌搜索表明,父类中必须有一个空的构造函数,但我已经有了它。
我知道编译语句是正确的,因为在使用 NTL 时除此之外没有其他方法。在这一点上,我没有解决这个问题的想法。提前致谢。
编辑 这个问题已经解决。我希望关闭或删除这个问题。
解决方案
一种解决方案是不对函数包装器使用模板。鉴于T
模板mpz_t
参数必须与mpz_set
. 模板似乎不适合这项工作。只需定义带有类型参数的包装器mpz_t
和const mpz_t
:
inline void assign(mpz_t C, const mpz_t A)
{
mpz_set(C, A);
}
您确实说过您想学习模板,但在不适当的环境中使用它们不会有那么大的帮助。而且您仍然拥有可供您的课程学习的模板。
话虽如此,我可以为您解释编译器消息。
警告:“注册”存储类说明符已弃用且与 C++1z [-Wdeprecated-register] 不兼容
for (register long i = NumBits(n)-2 ; i >= 0 ; i--)
这是一个容易修复的问题。摆脱该行中的“注册”。它不再是性能优化。
错误:没有匹配函数调用'assign'
assign(C,A);
[...]
注意:候选模板被忽略:推断参数'T'的冲突类型
编译器无法确定在此函数调用中将什么用作模板参数。有两个函数参数,每个参数都暗示模板参数assign
应该是什么。(这与 的模板参数不同expbin
,即使两者都命名为T
。)当含义发生冲突时,这是一个问题。完成这项工作的一种方法应该是指定您想要的参数,如
assign<T>(C, A);
这清楚地表明(在andassign
之间给出)的模板参数应该是(在此上下文中的含义)的模板参数。<
>
expbin
T
注意:您定义的模板看起来可以正常工作,而无需T
像这样指定。然而,mpz_t
从技术上讲,它是一个结构的数组(不仅仅是一个结构),用作参数的数组可能会衰减,这可能导致类型混淆。
错误:没有调用“mul”的匹配函数
mul(C, C, A);
注意:候选模板被忽略:推断参数“T”的冲突类型
相同(尽管在这种情况下有三个函数参数,所以推导出了三个候选T
)。
mul<T>(C, C, A);
推荐阅读
- javascript - 如何访问从 javaScript 中获取的 post 变量
- java - 启动 Tomcat 时“无法注入类 jenkins.slaves.IOHubProvider” - Tomcat 中的 Jenkins 安装
- java - 得到类 org.bouncycastle.asn1.DLApplicationSpecific 不能转换为类 org.bouncycastle.asn1.ASN1SequenceParser 使用 camel-as2 调用 as2-lib
- google-home - 如何知道用户何时取消链接谷歌助理操作?
- elasticsearch - Elasticsearch 获取与查询匹配的文档的兄弟文档
- swift - 在编译器期间,在 Swift 中为这个结构分配了多少内存
- python - 获取字典最小值的键,而该键在数组中
- xml - 如何使用 XSLT 在 XML 中查找不同的元素
- email - (Sendgrid v3 API)我的 API 命令有问题吗(我的电子邮件以垃圾邮件告终)?
- node.js - MUI - 如何查看 v4 的文档?