• C++类型转换运算符的重载,自增自减运算符的重载


    ​  C++里面各种各样的运算符都可以拿来重载,虽然不是所有的运算符都可以重载,但是绝大部分都是可以重载的,比方说这个类型转换运算符的重载,自增自减运算符的重载.

    C++类型转换运算符的重载

    我们知道C++中内置的一些类型之间是可以相互装换的:

    1. int a;
    2. double b=3.14;
    3. a=(double)b3;

    我们希望自己写的类也可以进行类型转化

    (1)将其他类型转换为我们写的类类型:只需要在构造函数中添加该类型的参数,然后将该参数的值赋给成员变量

    1. class Person
    2. {
    3. public:
    4.     int age;
    5.     Person(int i=0):age(i){
    6.     }
    7. };
    8. Person p;
    9. p = (Person)4;

    (2)将自己的类类型转化为其他类型,需要重载类类型操作符,函数形式如:operator 类型名称() const{返回其他类型的变量}

    1. class Person
    2. {
    3. public:
    4.     int age;
    5.     operator int() const{
    6.         return age;
    7.     }
    8. };
    9.  Person p;
    10.  p.age = 12;
    11.  int a = (int)p;

    上面的转换都是显示的转换,也可以写成隐式转换,Person p;p = 4;和Person p;p.age=12;int a = p;

    这样直接的隐式转换有时候会在我们不经意间就实现了,甚至我们本不想让其进行转换,所以为了避免这种情况。C++允许在上面的构造函数或者重载类类型的方法前面加上explicit关键字,之后就不能进行隐式的类型转换了。

    自增自减运算符的重载:

      自增和自减代表着哪两个运算符呢?

      自增:变量名"++"

      自减:变量名"- -"

      我们都知道自增运算符++、自减运算符--有前置/后置之分,为了区分所重载的是前,置运算符还是后置运算符,C++规定:

    前置运算符作为一元运算符重载
    重载为成员函数:
    T & operator++();
    T & operator--();
    重载为全局函数:
    T1 & operator++(T2);
    T1 & operator—(T2);
    后置运算符作为二元运算符重载,多写一个没用的参数:
    重载为成员函数:
    T operator++(int);
    T operator--(int);
    重载为全局函数:
    T1 operator++(T2,int );
    T1 operator—( T2,int);
    但是在没有后置运算符重载而有前置重载的情况下,
    定义一个obj,在vs中,obj++ 也调用前置重载,而dev则令 obj ++ 编译出错
    接下来我们来看几个代码例子:
    1. int main()
    2. {
    3. CDemo d(5);
    4. cout << (d++ ) << ","; //等价于 d.operator++(0);
    5. cout << d << ",";
    6. cout << (++d) << ","; //等价于 d.operator++();
    7. cout << d << endl;
    8. cout << (d-- ) << ","; //等价于 operator--(d,0);
    9. cout << d << ",";
    10. cout << (--d) << ","; //等价于 operator--(d);
    11. cout << d << endl;
    12. return 0;
    13. }
    输出结果:
    5,6,7,7
    7,6,5,5
      现在我们应该考虑的是CDemo这个类怎么编写?
      首先,一定要有4个重载函数,分别是:前置++,后置++,前置--,后置++,然后我们可以写一个类型转换运算符的重载.
    1. class CDemo {
    2. private :
    3. int n;
    4. public:
    5. CDemo(int i=0):n(i) { }
    6. CDemo & operator++(); //用于前置形式
    7. CDemo operator++( int ); //用于后置形式
    8. operator int ( ) { return n; }
    9. friend CDemo & operator--(CDemo & ); //友元函数,可以访问私有成员
    10. friend CDemo operator--(CDemo & ,int); //友元函数,可以访问私有成员
    11. };
    12. CDemo & CDemo::operator++()
    13. { //前置 ++
    14. n ++;
    15. return * this;
    16. } // ++s即为: s.operator++();
    17. CDemo CDemo::operator++( int k )
    18. { //后置 ++
    19. CDemo tmp(*this); //记录修改前的对象
    20. n ++;
    21. return tmp; //返回修改前的对象
    22. } // s++即为: s.operator++(0);
    23. CDemo & operator--(CDemo & d)
    24. {//前置--
    25. d.n--;
    26. return d;
    27. } //--s即为: operator--(s);
    28. CDemo operator--(CDemo & d,int)
    29. {//后置--
    30. CDemo tmp(d);
    31. d.n --;
    32. return tmp;
    33. } //s--即为: operator--(s, 0);
    注意:
    operator int ( ) { return n; }
    这里, int 作为一个类型强制转换运算符被重载 , 此后
    Demo s;
    (int) s ; // 等效于 s.int();
    类型强制转换运算符被重载时不能写返回值类型,实际上其返回值类型就
    是该 类型强制转换运算符 代表的类型
    完整代码:
    1. #include
    2. using namespace std;
    3. class CDemo {
    4. private :
    5. int n;
    6. public:
    7. CDemo(int i=0):n(i) { }
    8. CDemo & operator++(); //用于前置形式
    9. CDemo operator++( int ); //用于后置形式
    10. operator int ( ) { return n; }
    11. friend CDemo & operator--(CDemo & ); //友元函数,可以访问私有成员
    12. friend CDemo operator--(CDemo & ,int); //友元函数,可以访问私有成员
    13. };
    14. CDemo & CDemo::operator++()
    15. { //前置 ++
    16. n ++;
    17. return * this;
    18. } // ++s即为: s.operator++();
    19. CDemo CDemo::operator++( int k )
    20. { //后置 ++
    21. CDemo tmp(*this); //记录修改前的对象
    22. n ++;
    23. return tmp; //返回修改前的对象
    24. } // s++即为: s.operator++(0);
    25. CDemo & operator--(CDemo & d)
    26. {//前置--
    27. d.n--;
    28. return d;
    29. } //--s即为: operator--(s);
    30. CDemo operator--(CDemo & d,int)
    31. {//后置--
    32. CDemo tmp(d);
    33. d.n --;
    34. return tmp;
    35. } //s--即为: operator--(s, 0);
    36. int main()
    37. {
    38. CDemo d(5);
    39. cout << (d++ ) << ","; //等价于 d.operator++(0);
    40. cout << d << ",";
    41. cout << (++d) << ","; //等价于 d.operator++();
    42. cout << d << endl;
    43. cout << (d-- ) << ","; //等价于 operator--(d,0);
    44. cout << d << ",";
    45. cout << (--d) << ","; //等价于 operator--(d);
    46. cout << d << endl;
    47. return 0;
    48. }

    运算符重载这个单元算是彻底讲完了,给大家说一下注意事项:

    1. C++不允许定义新的运算符 ;
    2. 重载后运算符的含义应该符合日常习惯;
    1. complex_a + complex_b
    2. word_a > word_b
    3. date_b = date_a + n
    3. 运算符重载不改变运算符的优先级;
    4. 以下运算符不能被重载:“.”、“.*”、“::”、“?:”、sizeof;
    5. 重载运算符()、[]、->或者赋值运算符=时,运算符重载函数必须声明为
    类的成员函数。
      这就是我今天学习的类了!
  • 相关阅读:
    Shell编程之免交互
    X-ray diffraction
    几行代码把Chrome搞崩溃之:HTML5 MP3录音由ScriptProcessorNode升级成AudioWorkletNode采坑记
    网工内推 | 运维工程师,CCNP认证优先,周末双休,多次调薪机会
    java毕业设计-超市会员积分管理系统-Mybatis+系统+数据库+调试部署
    MySQL基础必会,简单易懂
    第3章 【MySQL】字符集和比较规则
    vue项目去掉网页滚动条
    【C++】运算符重载 ⑧ ( 左移运算符重载 | 友元函数 / 成员函数 实现运算符重载 | 类对象 使用 左移运算符 )
    JAVA【设计模式】享元模式
  • 原文地址:https://blog.csdn.net/wo_ai_luo_/article/details/127772172