【问题标题】:Boost MPL Types Vs TemplatesBoost MPL 类型与模板
【发布时间】:2016-03-22 16:16:32
【问题描述】:

我对 Boost MPL(以及一般的元编程)相当陌生,我认为我对模板与类型的概念感到困惑。我正在使用的一个简单示例是尝试计算向量的长度。以下编译正常:

typedef mpl::vector_c< int, 0, 1, 2, 3, 4, 5, 6, 7 > myVector;

struct TestSize
{
    template <typename mySequence> struct apply
    {
        typedef mpl::size<mySequence> type;
    };
};

typedef TestSize::apply<myVector>::type result;

但如果我在大小计算的结果中添加“::type”,如下所示:

struct TestSize
{
    template <typename mySequence> struct apply
    {
        typedef mpl::size<mySequence>::type type;
    };
};

typedef TestSize::apply<myVector>::type result;

然后我收到错误“错误:非类型“boost::mpl::size::type [with Sequence=mySequence]”不是类型名称”。

这是因为模板参数在嵌套命名空间中而没有推导出来的情况吗?更令我困惑的是以下编译:

struct TestSize
{
    template <typename mySequence> struct apply
    {
        typedef mpl::size<mySequence> type;
        typedef mpl::range_c<int, 0, type::type::value> myRange;
    };
};

typedef TestSize::apply<myVector>::type result;
typedef TestSize::apply<textureIndices>::myRange range;

为什么我可以在那里做“type::type::value”,但不能在前一行做“size::type”?

【问题讨论】:

    标签: c++ templates boost


    【解决方案1】:

    您出现此错误的原因是因为您需要像这样使用typename(在内部apply):

    struct TestSize
    {
        template <typename mySequence> struct apply
        {
            typedef typename mpl::size<mySequence>::type type; // <-- here!
        };
    };
    

    在这种情况下对typename 的需求源于编译器编译模板的方式。当模板最初被预编译时,它需要在语义上是正确的。但是,编译器(此时)不知道 mpl::size&lt;mySequence&gt;::type 确实是一种类型。此时它不知道mySequence 是什么,以及如何为mySequence 指定mpl::size。默认情况下,它假定 它不是类型。所以你需要提示它。

    现在你可能明白为什么type::type::value 可以正常工作了——编译器默认认为value 不是类型,你没有尝试将它用作类型,编译器很高兴。顺便说一句,如果您将value 定义为某个特化的类型,如果使用此特化,您会遇到一个有趣的编译错误!

    【讨论】:

    • @user1777820,你刚刚打开了这样一个潘多拉魔盒!简而言之,原因是mpl::size&lt;T&gt;::type 是一个template-dependent 名称。 type 的语义会根据T 的实际含义而有所不同——它可能是一个函数、一个类型、一个变量......任何东西。另一方面,size&lt;T&gt; 的语义不依赖于T——不管T 是什么,size&lt;T&gt; 只是一回事——它是先前定义的模板类size 的模板实例化。没有歧义,所以不需要暗示。
    • 我删除了我的评论,因为我要开始一个新问题,所以我将它添加回来以供将来阅读本文的任何人使用。我在问这里的解决方案,使用 typename 提示,与我的第一个代码示例有什么不同,行“typedef mpl::size type;”编译得很好。谢谢@SergeyA!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-30
    • 1970-01-01
    相关资源
    最近更新 更多