zoukankan      html  css  js  c++  java
  • [转]C++之运算符重载(2)

      上一节主要讲解了C++里运算符重载函数,在看了单目运算符(++)重载的示例后,也许有些朋友会问这样的问题。++自增运算符在C或C++中既可以放在操作数之前,也可以放在操作数之后,但是前置和后置的作用又是完全不同的(q前置运算符:先加1,再赋值;后置运算符:先赋值,再加1)。那么要怎么重载它们,才可以有效的区分开来呢?今天我就来说说C++中是怎么处理前置运算符和后置运算符的重载的。以及介绍一下插入运算符(>>)和提取运算符(<<)的重载。

      1.在C++里编译器是根据运算符重载函数参数表里是否插入关键字int来区分前置还是后置运算。比如:

    复制代码
     1 #include "stdafx.h"
    2 #include <iostream>
    3
    4 class TDPoint//三维坐标
    5 {
    6 private:
    7 int x;
    8 int y;
    9 int z;
    10 public:
    11 TDPoint(int x=0,int y=0,int z=0)
    12 {
    13 this->x=x;
    14 this->y=y;
    15 this->z=z;
    16 }
    17 TDPoint operator++();//成员函数重载前置运算符++
    18 TDPoint operator++(int);//成员函数重载后置运算符++
    19 friend TDPoint operator++(TDPoint& point);//友元函数重载前置运算符++
    20 friend TDPoint operator++(TDPoint& point,int);//友元函数重载后置运算符++
    21 void showPoint();
    22 };
    23
    24 TDPoint TDPoint::operator++()
    25 {
    26 ++this->x;
    27 ++this->y;
    28 ++this->z;
    29 return*this;//返回自增后的对象
    30 }
    31
    32 TDPoint TDPoint::operator++(int)
    33 {
    34 TDPoint point(*this);
    35 this->x++;
    36 this->y++;
    37 this->z++;
    38 return point;//返回自增前的对象
    39 }
    40
    41 TDPoint operator++(TDPoint& point)
    42 {
    43 ++point.x;
    44 ++point.y;
    45 ++point.z;
    46 return point;//返回自增后的对象
    47 }
    48
    49 TDPoint operator++(TDPoint& point,int)
    50 {
    51 TDPoint point1(point);
    52 point.x++;
    53 point.y++;
    54 point.z++;
    55 return point1;//返回自增前的对象
    56 }
    57
    58 void TDPoint::showPoint()
    59 {
    60 std::cout<<"("<<x<<","<<y<<","<<z<<")"<<std::endl;
    61 }
    62
    63 int main()
    64 {
    65 TDPoint point(1,1,1);
    66 point.operator++();//或++point
    67 point.showPoint();//前置++运算结果
    68
    69 point=point.operator++(0);//或point=point++
    70 point.showPoint();//后置++运算结果
    71
    72 operator++(point);//或++point;
    73 point.showPoint();//前置++运算结果
    74
    75 point=operator++(point,0);//或point=point++;
    76 point.showPoint();//后置++运算结果
    77
    78 return0;
    79 }
    复制代码

    结果:

    从示例代码里可以清楚的看出,后置运算符重载函数比前置运算符重载函数多了一个int类型的参数,这个参数只是为了区别前置和后置运算符,此外没有任何作用。所以在调用后置运算符重载函数时,int类型的实参可以取任意值。

      2.在C++中,操作符"<<"和">>"被定义为左位移运算符和右位移运算符。由于在iostream头文件中对它们进行了重载,使得它们可以用基本数据的输出和输入。

    复制代码
    #include "stdafx.h"
    #include <iostream>

    int main()
    {
    int a=10;
    std::cout<<"a="<<a<<std::endl;//运算符"<<"重载后用于输出
    a=a>>2;//右移运算符
    std::cout<<"右移2位:a="<<a<<std::endl;

    std::cout<<"请输入一个整数a:";
    std::cin>>a;//运算符">>"重载后用于输入
    a=a<<2;//左移运算符
    std::cout<<"左移2位:a="<<a<<std::endl;

    return0;
    }
    复制代码

    结果:

    插入运算符"<<"是双目运算符,左操作数为输出流类ostream的对象,右操作数为系统预定义的基本类型数据。头文件iostrem对其重载的函数原型为ostream& operator<<(ostream& ,类型名);类型名就是指基本类型数据。但如果要输出用户自定义的类型数据的话,就需要重载操作符"<<",因为该操作符的左操作数一定为ostream类的对象,所以插入运算符"<<"只能是类的友元函数或普通函数,不能是其他类的成员函数。一般定义格式:

      ostream& operator<<(ostream& ,自定义类名&);

    提取运算符">>"也是如此,左操作数为istream类的对象,右操作数为基本类型数据。头文件iostrem对其重载的函数原型为istream& operator>>(istream& ,类型名);提取运算符也不能作为其他类的成员函数,可以是友元函数或普通函数。它的一般定义格式为:

      istream& operator>>(istream& ,自定义类名&);

    我还是用上一节用的Complex类(复数类)来举例:

    复制代码
    #include "stdafx.h"
    #include <iostream>

    class Complex //复数类
    {
    private://私有
    double real;//实数
    double imag;//虚数
    public:
    Complex(double real=0,double imag=0)
    {
    this->real=real;
    this->imag=imag;
    }
    friend std::ostream&operator<<(std::ostream& o,Complex& com);//友元函数重载提取运算符"<<"
    friend std::istream&operator>>(std::istream& i,Complex& com);//友元函数重载插入运算符">>"
    };

    std::ostream&operator<<(std::ostream& o,Complex& com)
    {
    std::cout<<"输入的复数:";
    o<<com.real;
    if(com.imag>0)
    o<<"+";
    if(com.imag!=0)
    o<<com.imag<<"i"<<std::endl;
    return o;
    }

    std::istream&operator>>(std::istream& i,Complex& com)
    {
    std::cout<<"请输入一个复数:"<<std::endl;
    std::cout<<"real(实数):";
    i>>com.real;
    std::cout<<"imag(虚数):";
    i>>com.imag;
    return i;
    }

    int main()
    {

    Complex com;
    std::cin>>com;
    std::cout<<com;

    return0;
    }
    复制代码

    结果:

    出处:http://www.cnblogs.com/CaiNiaoZJ/archive/2011/08/13/2137033.html

  • 相关阅读:
    WCF系列(七) WCF安全系列(二) netTCPBinding绑定之Transport安全模式
    WCF系列(六) WCF安全系列(一) basicHttpBinding
    Convert .Net Program To Mono
    Adware:Win32/FastSaveApp 清除
    Python Http Get Post请求
    Python正则表达式应用示例
    Basic4android 使用Basic开发Android应用
    Decode Android AndroidManifest.xml file via C#
    Python工作记录
    趣文:程序员/开发人员的真实生活
  • 原文地址:https://www.cnblogs.com/GarfieldEr007/p/4646509.html
Copyright © 2011-2022 走看看