首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

使用using为成员模板类型定义别名会使编译器认为它不是类模板

成员模板是指在类模板中定义的函数模板或者类模板。在使用成员模板时,有时候需要为模板类型定义别名以方便使用。使用using关键字可以为成员模板类型定义别名。

然而,使用using为成员模板类型定义别名会导致编译器认为它不是类模板。这是因为using关键字会导致编译器将成员模板类型视为普通的函数或类,而不是模板。这可能会导致编译器无法正确推断模板参数类型,从而导致编译错误。

为了避免这个问题,可以使用typedef关键字来为成员模板类型定义别名。typedef关键字不会改变编译器对成员模板类型的认识,仍然将其视为类模板。这样可以确保编译器正确推断模板参数类型,并避免编译错误。

总结起来,使用using为成员模板类型定义别名会使编译器认为它不是类模板,可能导致编译错误。为了避免这个问题,建议使用typedef来为成员模板类型定义别名。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

模板的友元

counts()函数不是通过对象调用的(它是友元,不是成员函数),也没有对象参数,那么如何访问HasFriend对象的呢 有很多种可能性。...()本身并不是模板函数,而只是使用一个模板作参数。...(c++ 11) 如果能为类型指定别名,将很方便,在模板设计中尤其如此,可使用typedef 模板具体化指定别名: typedef std::array arrd; type std...定义一个模板别名,可使用它来指定类型,如下所示: arratype gallons;  // gallons是std::array类型 arratype...如果不希望buzz()是内联的,则应在一个单独的方法定义文件中定义。 共同的友元: 一个成员函数,它可以是一个成员,同时是另一个的友元,但有时将函数作为两个的友元更合理。

97670

c++中typename、typedef以及using关键字用法

在c++的标准库中,因为继承关系比较复杂和模板使用比较多的原因,源代码中充斥着typename、typedef和using这三个关键字,所以在继续剖析标准库源码之前,今天就来介绍一下这三个关键字的作用..._Vector_base; 最开始的时候声明模板形参,也会使用class,但我们都知道class总要是用来指定一个名,据说是为了避免混淆,所以后来增加了typename这个关键字,告诉编译器,跟在后面的字符串是一个不确定的类型...typename,实际上typename在这里也是指定后面的字符串类型,这是因为对于形如AA::BB这样的形式,它有可能是一个类型,也有可能是的静态成员,这个时候加上typename就是为了告诉编译器...;这样的形式告诉编译器,后续使用该命名空间里面的变量或者类型都无需再加上std的前缀,这个是对于命名空间整体的声明。...里面使用using声明以后,它可以被直接访问,其实这个时候的作用类似于引入命名空间中的变量,此处是引入父中的保护类型成员变量,对于这种用法,我们不展开多说,只要知道有这样的作用,以后看到了这样的代码知道它是怎么个意思就行了

92230

【笔记】《C++Primer》—— 第三部分:设计者的工具

朝bool类型进行转换是最常见的一种做法,但C11加入了显式类型转换来限制编译器不会隐式进行这个转换,也就是我们必须使用强制类型转换才能使用。...如果表达式不是引用也不是指针,则其动态类型永远与静态类型一致 派生可以往基类型转换,而基不能隐式反向转换 一个派生的函数如果想要覆盖继承来的虚函数,那必须名称和形参都一致,否则编译器认为这两个函数是独立的...定义方法是在声明函数名的时候函数体类似显式默认构造的写法改写=0,只能对虚函数使用这个写法 友元只对被声明的有效,友元的基或派生不是友元 某个对其继承来的成员的访问权限受到两个因素的影响:...要注意如果声明了目标友元的模板实参标识符,这些标识符需要与自身模板的标识符不同 我们不能用typedef来起模板类型别名,但是C11让我们可以用using来起模板类型别名 C11允许我们函数模板模板提供默认参数...16.2中有详细介绍 如果我们通过类型别名模板参数之类的方法间接定义了引用的引用(正常情况下无法定义),会产生引用的“折叠”,(X&)&,(X&)&&,(X&&)&都折叠X&,(X&&)&&折叠X

1.7K10

C++中typename的用法

作用域 在外部访问中的名称时,可以使用作用域操作符,调用通常存在三种:静态数据成员、静态成员函数和嵌套类型:Mydata::value,Mydata::function,Mydata...的一个成员;第二:定义一个指针,指针指向的类型T::iterator; 这样的话就会产生异议,由上面的介绍可以知道iterator是T的静态数据成员,静态成员函数或者是嵌套类型;如果没有修饰关键词...typename编译器可能认为我们是想实现乘法运算;若我们的本意是想定义一个指针时,这是就需要typename来修饰,即在T::iterator前面加上关键字typename;template <class...value _type;//定义一个别名..... };typename使用规则 typename在下面情况下禁止使用模板定义之外,即typename只能用于模板定义中非限定类型,比如int,...如果类型是依赖于模板参数的限定名,那么在之前必须加typename(除非是基列表,或者在的初始化成员列表中)。。

3K30

【C++11】让程序更简洁——模板

二、模板别名 在C98中,可以使用typedef重定义一个类型,如: typedef unsigned int uint_t; 在上面的代码中无符号整型类型被重新定义,但并不是新增一种类型,只是给已存在的类型重新定义了一个别名...using func_t = void (*)(int,int); 下面在来看下如何使用using语法,实现为一个模板定义一个别名。大家可以留言回复使用C98语法如何为一个模板定义一个别名。...,都不会新增一个类型,而是对原有类型进行重新定义一个别名。...using语法更加强大,编写出的代码更加简洁。 三、函数模板的默认模板参数 在C98中,模板可以有默认模板参数,函数模板中的默认模板参数是不被支持的,这一限制,在C++11中得到了解除。...如: func(123);//func的返回值long long 还有一种使用方式是将函数模板默认参数和模板参数自动推导一起使用,在一起使用时,如果函数模板无法自动推导,将会使用默认模板参数

65130

Modern c++快速浅析

using是C++11加入的,叫做_alias declaration_(别名声明)。...MyClassFunc = void(MyClass::*)(double, std::string) 除此之外,using能更方便的模板别名(alias templates),这是typedef...初学者选择typename可能会对模板有更好的了解(毕竟若模板传进来的是int,它是内置类型,看起来不是一个class) 进入正题,使用typename可以明确的告诉编译器,后面跟着的这个名字是中的类型成员..., PointTarget>::PointCloudSource; // C++11 template消歧义符 与typename类似,template修饰代表告诉编译器后面的东西是模板模板函数...那么我们可以认为这个Lambda所生成的匿名中,含有一个char类型和一个指针类型(this指针),由于内存对齐的缘故,这个Lambda类型的大小是8个字节 // 假设这是编译器生成的匿名 class

15710

【笔记】《C++Primer》—— 第16章:模板与泛型编程

模板程序应该尽量减少对实参类型的要求,例如比较大小时尽量使用小于号甚至使用less函数比较 编译器模板实例化(被输入具体参数引用)时才生成代码 为了生成实例化的模板,便因此需要掌握函数模板模板成员函数的定义...来起类型别名,但是C11让我们可以用using来起模板类型别名。...在起类型别名时我们会将整个模板作为一个别名,其中我们可以将一些参数固定住 // 模板的全参数别名 template using shortTemp...模板的名字可能是一个数据成员也可能是一个类型成员,默认情况下C++假定作用域运算符访问的名字不是类型,如果我们希望它是类型则需要在前面加typename标识 C11允许我们函数模板模板提供默认参数...通常情况下我们不能将左值传递给右值引用参数,但是C++设置了两个重要的例外来允许这种传递: 左值如i传递给模板类型的右值引用时,编译器会推断参数类型左值引用i& 如果我们通过类型别名模板参数之类的方法间接定义了引用的引用

1.5K30

从c++标准库指针萃取器谈一下traits技法

,最后是给别人使用的,所以对于类型而言,我们只要搞懂的公共成员都有些什么作用,那大概也就知道这个的作用了。...那么对于模板pointer_traits,的公共成员作用如下: pointer,这个其实就是模板参数_ptr的一个别名; element_type,也是一个别名,如果_ptr::element_type... { typedef _Tp* pointer; //特化类型取个别名 typedef _Tp element_type; //模板类型别名...,的公共成员与非特化其实是一致的,只是它是_Tp*类型提供的特化,对于其他公共成员,这里比较简单,就不再多说了,重点再看一下template using rebind这个类型别名模板...,直接获取一个_Up*类型的指针,结合整体来看,的作用就是:重绑定类型成员模板别名,使得可以由指向 _Tp 的指针类型,获取指向 _Up 的指针类型

82730

C++基础知识精髓

在C++中,结构可作为一种特殊的虽然可以包含函数,但是没有私有或受保护的成员。 C++中包含私有、公有和受保护成员,C++中可定义三种不同访控制权限的成员。...引用和指针 引用是一个别名,可以把看作变量本身,但是指针本身也是一个变量 引用在定义的时候必须初始化,必须绑定一个对象,如果一个对象本身不存在则取别名也没有意义。...内联函数的声明和定义是在一起的 在中声明和定义在一起的成员函数都默认为内联函数 内联函数和宏定义定义:在预处理阶段替换,但是容易产生二义性,不能作为成员函数访问私有成员。...通过对象指针进行的普通成员函数调用,仅仅与指针的类型有关,而与此刻指针正指向什么对象无关。想要实现当指针指向不同对象时执行不同的操作就必须将基中相应的成员函数定义虚函数。...编译器确保当对象派生时,派生的实现总是被调用,即使对象是使用指针访问而不是派生的指针。

2K50

实际工程中的 C++ 模板

在这篇文章里,我将聊一下最近实际工程中的一些模板的应用,希望可以让更多人了解到模板不是一个可怕的存在,以及一些常见的使用方式。...我们知道,C++ 的模板有个规则是 SFINAE,这不是一个单词,而是 Substitution Failure Is Not An Error 的缩写,也就是说,编译器在基于模板生成代码时,如果将模板类型参数置换为给定的类型时...> 里有很多 is_ 开头的模板就是基于这两个的,如果一个类型符合的约束,它就是 true_type 否则就是 false_type。...,使得函数签名本来就成为了注释的一部分,想要在 C++ 中实现类似的效果,我们可以不是using别名而是直接将类型包裹一层: struct Shape { Shape() = default...,这个模式里派生被作为基模板参数,这个声明看着有点吓人,但是实现的效果是很妙的: using Number = StrongAlias<uint8_t, struct NumberTag, Lt

2K20

Chapter 3: Moving to Modern C++

T的类型,因此就是一个依赖类型,C++规定依赖类型前面必须加上typename 如果使用alias定义模板,就不需要typename了 template using MyAllocList...T存在依赖关系的对象,但是当编译器处理Widget模板时,知道MyAllocList是一个类型的名字,因为MyAllocList是一个别名模板:必须命名一个类型,因此MyAllocList<T...为此,C++98只支持enum定义(列出所有的枚举值),而不支持声明,这使得在使用enum前,编译器能选择一个底层类型。...基和派生函数的const属性必须一致 基和派生函数的返回类型以及异常说明必须兼容 函数的引用修饰必须一致(C++11) 限制成员函数的使用只能是左值或者右值(*this) class Widget...,而且返回值void,并不是字面值常量,但是C++14中是允许的 10.

1.8K60

读完某C++神作,我只记下了100句话

内联函数避免函数调用的开销:编译时展开函数体中的表达式,免去函数调用的寄存器保存恢复、复制实参跳转等。 内联函数定义在头文件。编译器定义成员函数当做内联函数。...对于list对象应该优先使用list容器特有的成员版本【能添加删除元素】,而不是泛型算法。 简单说,就是定义了一个新的类型和一个新的作用域。成员访问级别默认私有。...初始化顺序由定义顺序决定,而不是初始化列表顺序。 友元:将非公有成员的访问权授予指定的或函数。friend在定义内部。友元引入的名和函数(定义或声明)可以像预先声明的一样使用。...对象不支持动态绑定,指针和引用支持但使用起来麻烦,解决方法是定义包装或句柄【提供到其它接口的】。像使用指针一样使用句柄而不用管理指向的对象。类似智能指针的方法建立指针句柄。...模板特化:template 模板名函数形参表 函数体 特化 也可以只特化中某个成员 部分特化:多个模板形参,特化某个形参【编译器会优先选择特化的】。

1.4K20

小朋友学Python(10):CC++JavaPython的关键字

extern, export 为了访问其他编译单元(如另一代码文件)中的变量或对象,对普通类型(包括基本数据、结构和),可以利用关键字extern,来使用这些变量或对象时;但是对模板类型,则必须在定义这些模板对象和模板函数时...inline 声明定义内联函数,提示编译时内联——将所调用的代码嵌入到主调函数中。注意是否内联取决于实现——编译器有权不实际内联,如果认为这是必要的或更符合预期的目标代码质量。...若返回类型不是void可以同时带返回值。 static 和C语言类似,声明静态存储期对象。在C++还有另一个用途——用于作用域声明,表示声明的成员共有的,不需要通过的对象访问。...sizeof 返回类型名或表达式具有的类型对应的大小。 template 声明模板,实现泛型和参数化编程。 this this是一种实体,仅在的非静态成员使用,是指向的对象的指针。...typeid是操作符,不是函数。 typename 告诉编译器是一个类型不是一个成员。 用在模板定义里,标明其后的模板参数是类型参数,是class的同义词,可被class代替。

1.3K80

c++模板与泛型编程

我们上面的compare模板定义的就是一个类型参数,表示一个类型,而一个非类型模板参数则表示一个值,通过一个特定的类型来指定。...此外,为了生成一个实例化版本,编译器需要掌握函数模板模板成员函数的定义。...默认情况下,一个模板成员函数只有当程序用到时才进行实例化。 在模板自己的作用域中,我们可以直接使用模板名而不提供实参。...在模板使用时,名和返回值类型必须提供模板参数,在函数体内,由于已经进入的作用域,所以无需重复模板实参,默认与成员实例化所用类型一致。...因此,如果希望使用一个模板类型参数的类型成员,必须显式告诉编译器该名字是一个类型typename T::value_type。

58720

《C++Primer》第十六章 模板与泛型编程

通常当我们调用一个函数时,编译器只需要掌握函数的声明。类似地,当我们使用一个类型的对象时,定义必须是可用的,但是成员函数的定义不必已经出现。...Blob StrBlob;d 由于模板不是一个,因此我们不能定义一个typedef引用Blob,但是新标准允许我们模板定义一个类型别名: template <typename...3.2 使用类型成员 我们用作用域运算符::来访问static成员类型成员,在普通(非模板)代码中,编译器掌握定义,因此直到通过作用域运算符访问的名字是类型还是static成员。...对于模板,我们也可以定义成员模板,这种情况下,成员各自有自己的、独立的模板参数。...因此,当我们调用f3(i))时,编译器推断T的类型int&而非int 通常我们不能(直接)定义一个引用的引用,但是通过类型别名或通过模板类型参数间接定义是可以的 第二个例外规则:如果我们间接创建一个引用的引用

1.7K10

基于STL源码分析deque容器整体实现及内存结构

1. deque容器整体源码实现介绍 deque容器是stl中顺序容器的一种,之前已经介绍过array和vector了,今天介绍deque容器,deque的本质是一个模板的声明位于头文件bits/...下面对这个图进行一个简单的解读: deque容器保护继承于模板_Deque_base,也就是_Deque_base是deque的基,并且内存分配和释放都是通过基来完成的; 容器首地址和迭代器等保存在结构体成员变量..._M_impl中,继承于别名类型_Tp_alloc_type,最终的内存分配其实就是通过完成的; deque容器使用了它自己的迭代器_Deque_iterator,没有直接使用stl中的公共迭代器,...,在c++11以后,使用模板pointer_traits的rebind类型属性,有关pointer_traits的详细说明,请看下面这篇文章: 从c++标准库指针萃取器谈一下traits技法 仔细看一下...简单的定义了一个deque,元素个数1024,每一个元素值100。

58440

模板

使用模板: 仅在程序包含模板并不能⽣成模板,⽽必须请求实例化。 需要声明⼀个类型模板的对象,⽅法是使⽤所需的具体类型替换泛型名。...编译器可以创建 ,但使⽤效果如何就因⼈⽽异了。 不正确的使用指针栈 切忌盲目使用模板 正确使用指针栈 方法: - 让调⽤程序提供⼀个指针数组,其中每个指针都指向不同的字符串。...Arraytp_H_ ``` - 关键字class(或在这种上下⽂中等价的关键字typename)指出T**类型参数**, - int指出n的类型int,这种参数(指定特殊的类型不是⽤...eggs(12); Stack dunkers(13); ``` - 另⼀个区别是,构造函数⽅法更通⽤,这是因为数组⼤⼩是作为**成员**(⽽不是硬编码)存储在定义中的...这是因为 名是Pair,⽽不是Pair。 - Pair是另⼀个完全不同的的名称。 默认类型模板参数 模板的具体化: 成员模板: 将模板用作参数: 模板和友元: 模板别名

3K20

查看自动类型推导结果的方法

需要注意的是,这个工具我发现了一个Bug,就是上面代码中的T9类型别名,正确的类型应该是func函数的类型:int(int, int),这里显示的返回值的类型了。...编译时打印编译器肯定是知道变量的类型的,但是没法直接告诉你,有一个可以让编译器告诉你的办法,就是编译发生错误时编译器在报告的错误信息中肯定会提到导致此错误的类型,因此我们可以声明一个如下的模板:template...所以我们想要查看哪个变量的类型,只要将这个变量的类型作为模板的形参去实例化,就会导致一个错误,在编译器给出的错误信息里就会显示出这个变量的具体类型,如下所示:const int x1 = 1;auto...,这时候可以借助C++的RTTI特性,C++标准库提供了typeid函数和type_info,对变量或者类型调用typeid会返回一个type_info对象,type_info里有一个成员函数name...这时可以采用另外一种手段来输出变量的类型,跟上小节中的例子一样借助模板的技术,实现一个模板函数,在模板函数中利用编译器提供的宏,把这个函数的原型打印出来,函数原型中就包含了函数的参数个数及其类型,这个宏由于不是

7710

《Effective C++》学习笔记

对于(非模板),标准std::swap提供一个特定版本(swap是模板函数,可以特化)。 在使用swap时,记得 using std::swap,让编译器可以获取到标准swap或特化版本。...实现 条款26:尽可能延后变量定义式的出现时间 尽可能延后变量定义式的出现,既包括延后构造,保证只有真正使用才构造;也包括只有到赋值时才构造,避免默认构造函数无畏调用。...如果是 is-a 的关系,可以用继承,但如果是 has-a 的关系,应该将一个作为另一个成员变量来使用,以利用该类的能力,而不是去以继承的方式使用。...条款46:需要类型转换时请模板定义成员函数 模板中的模板函数不支持隐式类型转换,如果你在调用时传了一个其他类型的变量,编译器无法帮你做类型转换,从而报错。...解决方案是将该模板函数定义模板内的友元模板函数,从而支持了参数的隐式转换。

1.1K20
领券