根据类型模板的类型参数自动执行其大小参数

Fra*_*ler 0 c++ templates template-specialization argument-deduction c++17

使用类模板时,是否可以通过推断其类型来指定特定大小?这是一个伪代码示例,代表我要询问的内容。

#include <bitset>
#include <cstdint>

namespace xxx {

#define BYTE  8
#define WORD  16
#define DWORD 32
#define QWORD 64

    typedef std::uint8_t   u8;
    typedef std::uint16_t u16;
    typedef std::uint32_t u32;
    typedef std::uint64_t u64;

    template<typename Type, u16 BitCount>
    struct Register {
    };
}
Run Code Online (Sandbox Code Playgroud)

我不知道我可以使用部分专业化还是完全专业化,而且我也不知道该怎么做。我想做的是以下几点:

  • 如果Type==,u8BitCount自动== BYTE8
  • 如果Type==,u16BitCount自动== WORD16
  • 如果Type==,u32BitCount自动== DWORD32
  • 如果Type==,u64BitCount自动== QWORD64

这样做的原因是,当涉及到上面的类及其成员时,我还没有显示,但是在这里将要显示的是,它的成员之一是 std::bitset

template<typename Type, u16 BitCount>
struct Register {
   Type value;
   std::bitset<BitCount> 
};
Run Code Online (Sandbox Code Playgroud)

是的,我知道我可以这样实例化它们:

void someFunc() {
    Register<u8, 8> r8;
    Register<u16, 16> r16;
}
Run Code Online (Sandbox Code Playgroud)

但是我希望能够专门化它们,这样您就不必传递任何参数类型,我希望可以通过传入的参数类型来推导它们,或者,如果只是传递类型,那么大小部分是自动的。这将是首选

void someFunc() {
    Register<u8> r8;
} 

// the class would automatically use `8` for its `std::bitset<8>` member.
Run Code Online (Sandbox Code Playgroud)

其基础类型和位大小始终存在一对一的对应关系。

这种实例化是无效的:

Register<u32, 64> reg; // invalid type u32 can only be 32...
Run Code Online (Sandbox Code Playgroud)

是否有通过专门化,继承,多态等方法来执行此操作的已知方法?

Som*_*ken 5

您可以只使用usings:

using u8Register = Register<u8, BYTE>;
using u16Register = Register<u16, WORD>;
using u32Register = Register<u32, DWORD>;
using u64Register = Register<u64, QWORD>;
Run Code Online (Sandbox Code Playgroud)

或者,如果这些类型与其字节大小一一对应,则可以使用sizeof

#include <limits.h>
template<typename Type, u16 BitCount = sizeof(Type) * CHAR_BIT>
struct Register {
   Type value;
   std::bitset<BitCount> 
};
Run Code Online (Sandbox Code Playgroud)

或者,您可以继承来Register进行专门研究。

  • 我很难弄清楚你的意思。sizeof(type)* CHAR_BIT是类型的大小,以位为单位。这是一个constexpr,因此您可以将其用作模板参数。这就是全部。 (2认同)