IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> C++知识库 -> 用 using 还是 typedef -> 正文阅读

[C++知识库]用 using 还是 typedef

  1. 总览

    • usingtypedef好在哪些地方.

      • using支持模板的别名.

      • using有编译器加持.

    • 相同点

      • 都是别名,不过using的看起来更加简洁.

  2. 相同点

    • 别名

      #include<iostream>
      using Myshow = void (*)();
      typedef void(*Dshow)();
      void show() {
         std::cout << __LINE__ << std::endl;
      }
      
      
      int main() {
         Myshow{&show}();
         Dshow{&show}();
         // 二义性,优先定义,而非初始化.
         // Dshow(&show)();
      }
      
      • 都挺简单,但是typedef的有点略难懂.

  3. 模板别名

    • using

      #include<iostream>
      #include<vector>
      
      template<typename T>
      using Myvector = std::vector<T>;
      
      int main() {
         Myvector<int> b{1,2,3};
         for(const auto& a : b) {
             std::cout << a << std::endl;
         }
      }
      
      • 正常编译执行

    • typedef模仿

      #include<iostream>
      #include<vector>
      
      template<typename T>
      typedef std::vector<T> Myvector;
      
      int main() {
         Myvector<int> b{1,2,3};
         for(const auto& a : b) {
             std::cout << a << std::endl;
         }
      }
      
      • 编译报错

    • 改改typedef

      #include<iostream>
      #include<vector>
      
      template<typename T>
      struct Myvector {
         typedef std::vector<T> type;
      };
      
      
      int main() {
         Myvector<int>::type b{1,2,3};
         for(const auto& a : b) {
             std::cout << a << std::endl;
         }
      }
      
      • 勉强可以用,但是不够简洁了呀.

  4. 别名类型做成员变量

    • using

      #include<iostream>
      #include<vector>
      
      template<typename T>
      using Myvector = std::vector<T>;
      
      template<typename T>
      class Temp {
      public:
         Myvector<T> a;
      };
      
      int main() {
         Temp<int> b{{1,2,3}};
         for(const auto& a : b.a) {
             std::cout << a << std::endl;
         }
      }
      
      • 正常输出123.

    • typedef

      #include<iostream>
      #include<vector>
      
      template<typename T>
      typedef std::vector<T> Myvector;
      
      template<typename T>
      class Temp {
      public:
         Myvector<T> a;
      };
      
      int main() {
         Temp<int> b{{1,2,3}};
         for(const auto& a : b.a) {
             std::cout << a << std::endl;
         }
      }
      
      • 这种肯定编不过.上面都编不过。

    • typedef改改版

      #include<iostream>
      #include<vector>
      
      template<typename T>
      struct Myvector {
         typedef std::vector<T> type;
      };
      
      
      template<typename T>
      class Temp {
      public:
         Myvector<T>::type a;
      };
      
      int main() {
         Temp<int> b{{1,2,3}};
         for(const auto& a : b.a) {
             std::cout << a << std::endl;
         }
      }
      
      • 用上面的改一改,加内置了,编译报错.

      • 因为不知道type是类型还是变量名.无法预测未来.

    • 可行版typedef

      #include<iostream>
      #include<vector>
      
      template<typename T>
      struct Myvector {
         typedef std::vector<T> type;
      };
      
      
      template<typename T>
      class Temp {
      public:
         typename Myvector<T>::type a;
      };
      
      int main() {
         Temp<int> b{{1,2,3}};
         for(const auto& a : b.a) {
             std::cout << a << std::endl;
         }
      }
      
      • 这种是可行的,但是看起来好麻烦.

      • 必须通过关键字typename告诉编译器Myvector<T>::type是一个类型而不是变量.

    • 小结

      • typedefc++11没有办法完美的适应环境了.

      • 间接类型需要用typename声明其是类型不是变量名.编译器笨吧.

      • using命名后的就不需要也不允许typename的出现了.

    • 小疑问

      • Myvector<T>::type如果是类型,Myvector<T>::type()就是匿名对象创建,调用默认构造.或者是函数声明?
      • Myvector<T>::type如果是变量名,恰好是个可调用对象,那么就是匿名返回值. 无法解析.语义都不一样了.
  5. 为什么不增强typedef的功能

    • 开发就需要做到,不改原来的基础上增加新的功能. 开闭原则.

  6. C++标准库的实现

    • type_traits

      • 主要是用在元模板编程了.

      • 可以通过传入类型然后返回这个类型的另外的类型,比如加减修饰.

      • const类型获取对应的非const类型.&类型获取到对应的非引用类型.

    • 获取某个类型的普通版本变量

      #include <iostream>
      #include <type_traits>
      
      int main() {
         const int a = 0;
         std::remove_const<decltype(a)>::type b;
         b = 1;
         return 0;
      }
      
      • 得到这个变量的普通版本.

      • 不太好看,每次都要加一个::type.

    • using版本

      #include <iostream>
      #include <type_traits>
      
      template <typename T>
      using remove_const_t = typename std::remove_const<T>::type;
      
      int main() {
         const int a = 0;
         remove_const_t<decltype(a)> b;
         b = 1;
         return 0;
      }
      
    • typedef

      • 无法支持,只能在内部类中创建.

    • type_traits

      • c++11使用的typedef在内部实现的这种机制.

      • c++14的时候才采用typedef的方式实现.remove_const_t的形式. 如上.

  7. 总结

    • using在模板别名方面表现比typedef好.

    • using有编译器加持.

    • 间接名需要用typenametypedef不需要.

  C++知识库 最新文章
【C++】友元、嵌套类、异常、RTTI、类型转换
通讯录的思路与实现(C语言)
C++PrimerPlus 第七章 函数-C++的编程模块(
Problem C: 算法9-9~9-12:平衡二叉树的基本
MSVC C++ UTF-8编程
C++进阶 多态原理
简单string类c++实现
我的年度总结
【C语言】以深厚地基筑伟岸高楼-基础篇(六
c语言常见错误合集
上一篇文章      下一篇文章      查看所有文章
加:2021-12-18 15:47:14  更:2021-12-18 15:49:46 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 14:01:28-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码