我可以存储一个姓名吗?

时间:2017-08-06 14:11:36

标签: c++

这是我访问内存的示例类:

class memory {
  public:
    memory();

    template <typename T>
    T get(int index);
    template <typename T>
    void set(int index, T value);
};

我在这里使用它:

int main(){
  memory mem;

  float f = mem.get<float>(0);
  char* str = mem.get<char*>(1);

  mem.set<float>(0, 25);  // int passed, upgraded to float

  return 0;
}

我想以这种方式使用它:

int main(){
  memory<float, char*> mem;  // typenames defined only once. Must accept a variable number of template arguments

  float f = mem.get(0);
  char* str = mem.get(1);

  mem.set(0, 25);  // int passed, upgraded to float

  return 0;
}

我该如何实现?它甚至可能吗?

1 个答案:

答案 0 :(得分:1)

您似乎想要std::tuplehana::tuple。完全有可能改变你的课程,这样你就不必每次都发送这个类型。

但是,您仍需要传递某些内容作为模板参数。通常,变量的索引或类型的索引就足够了。

标准库中的tuple类是这样的:

std::tuple<int, std::string> tup;

std::get<0>(tup) = 5; // assign the int
std::get<1>(tup) = "test"; // assign the string

以类似的方式提升它的天空,但使用operator[]

hana::tuple<int, std::string> tup;

tup[0_c] = 5; // assign the int
tup[1_c] = "test"; // assign the string

_c是用户提供的文字,它将int转换为整数常量,因此可以在编译时使用该值。

那你怎么做呢?

只需将int参数更改为模板参数:

int main() {
  memory<float, char*> mem;

  float f = mem.get<0>();
  char* str = mem.get<1>();

  mem.set<0>(25);  // int passed, upgraded to float

  return 0;
}

然后,根据索引推断出类型是什么,请使用以下内容:

template<std::size_t, typename>
struct memory_element; // no basic case

// In this case, we pass a number and a memory class
// We extend the case were the index is decremented, and we remove the first type.
template<std::size_t index, typename Head, typename... Tail>
struct memory_element<index, memory<Head, Tail...> : memory_element<index - 1, memory<Tail...>> {};

// Case where we get to 0
template<typename T, typename... Rest>
struct memory_element<0, memory<T, Rest...>> {
    using type = T;
};

// Alias for ease of use
template<std::size_t I, typename M>
using memory_element_t = typename memory_element<I, M>::type;

您可以像这样使用它:

int main () {
    // T1 is int
    using T1 = memory_element_t<0, memory<int, float>>;

    // T2 is float
    using T2 = memory_element_t<1, memory<int, float>>;
}