当前位置: 首页 > 知识库问答 >
问题:

将变量模板包装为元组向量

段渊
2023-03-14

使用C 14,我试图扩展此实现,以支持将在外部调用的ObserverCallback方法

MyClass容器使用元组向量,其类型由可变模板指定。然后可以使用Access访问vector

我需要的是实现一个观察器,它应该向向量添加元素。由于元素的类型可以是元组中的任何类型,因此我也对其进行了模板化:

template <typename ...T>
class Wrapper{
public:
    MyClass<T...> mc;

    template <typename U>
    void ObserverCallback(const U& element){
        mc.access<U>().push_back(element);
    }
};

包装器类中似乎有错误:

variadic2.cpp: In member function 'void Wrapper<T>::ObserverCallback(const U&)':
variadic2.cpp:71:20: error: expected primary-expression before '>' token
         mc.access<U>().push_back(element);
                    ^
variadic2.cpp:71:22: error: expected primary-expression before ')' token
         mc.access<U>().push_back(element);
                      ^
variadic2.cpp: In function 'int main(int, char**)':
variadic2.cpp:87:10: error: 'class MyClass<float, std::reference_wrapper<int>, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >' has no member named 'ObserverCallback'
     w.mc.ObserverCallback(string("a"));

作为参考,我还附上完整的源代码清单:

#include <tuple>
#include <vector>
#include <functional>
#include <iostream>
#include <string>

using namespace std;

template <class T1, class T2>
struct SameType
{
    static const bool value = false;
};

template<class T>
struct SameType<T, T>
{
    static const bool value = true;
};

template <typename... Types>
class MyClass
{
     public:
     typedef tuple<vector<Types>...> vtype;
     vtype vectors;

     template<int N, typename T>
     struct VectorOfType: SameType<T,
        typename tuple_element<N, vtype>::type::value_type>
     { };

     template <int N, class T, class Tuple,
              bool Match = false> // this =false is only for clarity
     struct MatchingField
     {
         static vector<T>& get(Tuple& tp)
         {
             // The "non-matching" version
             return MatchingField<N+1, T, Tuple,
                    VectorOfType<N+1, T>::value>::get(tp);
         }
     };

     template <int N, class T, class Tuple>
     struct MatchingField<N, T, Tuple, true>
     {
        static vector<T>& get(Tuple& tp)
        {
            return std::get<N>(tp);
        }
     };

     template <typename T>
     vector<T>& access()
     {
         return MatchingField<0, T, vtype,
                VectorOfType<0, T>::value>::get(vectors);
     }
};

template <typename ...T>
class Wrapper{
public:
    MyClass<T...> mc;

    template <typename U>
    void ObserverCallback(const U& element){
        mc.access<U>().push_back(element);
    }
};

int main( int argc, char** argv )
{
    int twelf = 12.5;
    typedef reference_wrapper<int> rint;

    Wrapper<float, rint, string> w;
    vector<rint>& i = w.mc.access<rint>();

    i.push_back(twelf);

    w.mc.access<float>().push_back(10.5);

    w.ObserverCallback(string("a"));

    cout << "Test:\n";
    cout << "floats: " << w.mc.access<float>()[0] << endl;
    cout << "ints: " << w.mc.access<rint>()[0] << endl;
    cout << "strings: " << w.mc.access<string>()[0] << endl;
    //w.access<double>();

    return 0;
}

共有1个答案

施学
2023-03-14

mc的类型取决于T...,因此必须指定其访问成员应该是函数模板:

mc.template access<U>().push_back(element);
// ^^^^^^^^
 类似资料:
  • 我试图将两个向量的元组包装成C中的元组,但无法解码神秘的编译器错误消息。 以下是代码片段(请原谅我使用指令): 这是Visual Studio 2010中的错误消息 我的代码有什么问题? <罢工>编辑:如果我显式地声明了结果类型,那么它是有效的。 编辑:假警报,如果我声明的类型,它也不会编译。

  • 问题内容: 我使用“消息”界面将消息传递给用户,如下所示: 我想在变量中包含html 并呈现它,而不在模板中转义标记。 问题答案: 如果你不想转义HTML,请查看过滤器和标签: safe: autoescape:

  • 问题内容: 我试图将值放入“标题”模板中,例如标题和导航链接,但无法访问我从包含的模板发送到主模板的变量。 渲染模板: index.html模板: header.html模板: 显然,它不会那样工作。 也许有一种方法可以解析/获取模板并将变量放入其中,而无需将整个头文件放入代码中?然后,我可以将该模板作为变量发送到我的主模板。但这似乎并不是最好的方法。 问题答案: 您可以在调用模板时将上下文传递给

  • template.defaults.imports 模板通过 $imports 可以访问到模板外部的全局变量与导入的变量。 导入变量 template.defaults.imports.log = console.log; <% $imports.log('hello world') %> 内置变量清单 $data 传入模板的数据 $imports 外部导入的变量以及全局变量 print 字符

  • 问题内容: 有没有一种方法可以将模板呈现为变量而不是输出? 像这样的东西 问题答案: 在您的示例中,最简单的方法是将回调传递给: 但是,如果要渲染局部模板以便将其包含在另一个模板中,则绝对应该查看视图局部。

  • 我想确认这个代码是合法的(还是不合法的?)C++17。 如果用G++和MSVC编译,我不会得到错误(并得到正确的输出), 但Intel和clang给出了一个错误: 使用编译(对于MSVC)。 在godbolt和我的本地机器上尝试了最新的编译器。