2

如果我使用带有 int 模板参数的 C++ 类,例如:

template<int width> class ap_uint { ... }

然后我知道我可以从这种类型的某些宽度创建特定定义,例如:

typedef ap_uint<72> data_t;

但是,如果我想说定义一个常量并将其传入,我的选择是什么(除了定义)?说这样的话:

#define WIDTH 72
typedef ap_uint<WIDTH> data_t;
typedef ap_uint<WIDTH / 8> mask_t; // Does this even work?

此外,是否可以在模板参数选择中定义一个函数或使用现有函数?像这样的东西:

#define SIZE 1024
typedef ap_uint<ceil(log(SIZE, 2))> addr_t;

如果可能的话,我可以自己编写函数。

4

2 回答 2

4

模板参数必须是常量表达式。因此,您的选项包括产生常量表达式(特别是函数)的#define、和和 表达式/函数。是现代 C++ 的做法。 enumconst intconstexpr intconstexprconstexpr int

WIDTH / 8确实有效。

本质上它必须是一个编译时常量

于 2019-07-27T20:16:01.727 回答
3

一些观察,没有特别的顺序。

(1)你标记了 C++11,所以不仅typedef(更好,恕我直言)还有using

using data_t = ap_uint<72>;

(2) 你也可以“模板化”using

template <int I>
using data_t = ap_uint<I+3>;

(3)“这甚至有效吗?”

#define WIDTH 72    
typedef ap_uint<WIDTH / 8> mask_t; 

作品。

但是,鉴于您标记了 C++11,我建议您避免#define使用constexpr常量来代替

constexpr auto WIDTH = 72;

using mask_t = ap_uint<WIDTH / 8>; 

(4)“是否可以在模板参数选择中定义一个功能或使用现有的功能”

在 C++11 之前,答案是:不。

但是你标记了 C++11 所以答案是:是的,但是函数必须是constexpr一个

例子

constexpr int foo (int a)
 { return a+3; }

constexpt int bar = 42;

using data_t = ap_uint<foo(bar)>; // compile: foo(bar) is a constant expression

int baz = 42;

using data_t2 = ap_uint<foo(baz)>; // compilation error! baz isn't a constant 
                                   // expression so foo(baz) isn't

std::ceil()( 5)std::log()并非constexpr如此

#define SIZE 1024
typedef ap_uint<ceil(log(SIZE, 2))> addr_t;

不编译

(6) “如果可能的话,我可以自己编写函数。”

从 C++11 开始,这是可能的(参见第 (4) 点的示例)。

不幸的是,只有从 C++14 开始,才有可能编写复杂的constexpr函数。

在 C++11 中,一个constexpr函数几乎只能包含(简化一点)一条return指令。

于 2019-07-27T20:27:10.007 回答