C++复习第三天 运算符重载

来源:互联网 发布:小怪兽 知乎 编辑:程序博客网 时间:2024/06/08 04:33
/**运算符重载的本质就是函数调用**/#include <iostream>#include <stdlib.h>#include <string.h>//转载请注明:http://blog.csdn.net/oyhb_1992/article/details/78018555using namespace std;class mystring{public:  //private    char *s;public:    mystring()    {        s = new char[1024];        cout << "mystring" << endl;    }    mystring(const mystring &it)//深拷贝    {        //因为重载了=运算符,所以想要调用拷贝构造只能mystring str1(str2);        //而不能用 mystring str1 = str2;        cout << "copy mystring" << endl;        s = new char[1024];        memset(s, 0, 1024);        strcpy(s, it.s);    }    ~mystring()    {        cout << "~mystring" << endl;        delete []s;    }    mystring operator =(const mystring &it)//重载了一个=号操作符    {        //mystring str2 = str1;        cout << "= operator" << endl;        memset(s, 0, 1024);        strcpy(s, it.s);        return *this;    }    mystring operator =(const char *str)//重载了一个=号操作符    {        // mystring str1 = “test”;        memset(s, 0, 1024);        strcpy(s, str);        return *this;    }    mystring operator =(int i)//重载了一个=号操作符    {        // mystring str1 = 10;        memset(s, 0, 1024);        sprintf(s, "%d", i);        return *this;    }    mystring operator + (const mystring &it)//重载了一个+号操作符    {         // mystring str1 = str2 + str3;        strcat(s, it.s);        return *this;    }    mystring operator + (const char *str)//重载了一个+号操作符    {        // mystring str1 = str2 + "test";        strcat(s, str);        return *this;    }    void operator +=(const char *str)//    {        // mystring str1 += "test";        strcat(this->s, str);//注意不用返回对象    }    mystring operator + (int i)//重载了一个+号操作符,一元操作符重载    {        char temp[100] = {0};        sprintf(temp, "%d", i);//sprintf函数是printf输出到数组        strcat(s, temp);        return *this;    }    void operator <<(const char *str)//把<<操作符定义为赋值,类似于cout重载了<<    {        //str3 << "CCCCC";        strcpy(s, str);    }    void operator >>(char *str)//把<<操作符定义为赋值    {        //char buf[1024] = {0};        //str3 >> buf;        strcpy(str, s);    }    mystring operator ++(int)//重载前++操作符的函数int参数是固定格式    {    //str1 = str2++;        int len = strlen(s);        for(int i = 0;i < len; i++)        {            s[i]++;//让s的第一个成员char + 1,就是将s[0]对应字符的ASCII码 + 1        }        return *this;    }    void * operator new(size_t size)//如果重载的new,那么必须重载delete    {        //mystring *pstr = new mystring;        //参数size就是sizeof(mystring)的大小.        cout << "size = " << size << endl;        mystring *p = (mystring *)malloc(size);        return p;    }    void operator delete(void *obj)    {        free((mystring *)obj);//不能直接free一个void *,强转就知道要释放多大的内存        obj = NULL;//防止野指针    }    void * operator new[](size_t size)//如果重载new,那么必须重载delete    {        //参数size = sizeof(mystring) * new[x] + 4个字节(这4个字节用来存储        //分配的内存大小,在delete时要知道要释放多大内存).        cout << "size = " << size << endl;        mystring *p = (mystring *)malloc(size);        return NULL;    }    void operator delete[](void *obj)    {        free((mystring *)obj);        obj = NULL;    }    bool operator ==(const mystring &it)    {        if (strcmp(s, it.s) == 0)//如果this->s和it的s相同,就返回true        {            return true;        }else            return false;    }    bool operator ==(const char *str)    {        if (strcmp(s, str) == 0)//如果this->s和it的s相同,就返回true        {            return true;        }else            return false;    }    //如果返回的是char,代表的是一个右值,右值是不能直接赋值的,    //如果返回的是char的引用,那么[]就可以当左值使用了,左值是可以修改赋值的    char &operator[](int index)    {        return s[index];    }    void operator ()(const char *str)//重载函数调用操作符    {   //str1("aaaaaaa");        strcpy(s, str);    }    void operator ()(int i)    {   //str1(10);        sprintf(s, "%d", i);    }    //重载强制转换操作符,不能有返回值,这是格式要求    operator int()    {        //mystring str = "123";        //int i = int(str);        return atoi(s);    }    friend mystring operator +(const char *str, const mystring &it);//友元    friend mystring operator ++(mystring &it);//友元};/******************内外运算符重载**************************/bool operator ==(const char *str, const mystring &it){    //("test" == str1)    if (strcmp(str, it.s) == 0)    {        return true;    }else        return false;}/*对于二元操作符重载,如果操作符左边是类,那么就在该类内部成员函数重载操作符即可            如果操作符左边是常量,那么就必须在类的外部定义一个操作符重载函数*///操作符重载,有一个最基本条件,就是一定有一个一元是一个自定义的C++类//如果两个都是基本数据类型操作符重载是非法的,所以友元函数用在运算符重载里最多//str3 = "AAAAA" + str1;操作符的本质是函数调用,如果操作符左边是常量谁去调用函数啊?mystring operator +(const char *str, const mystring &it){    mystring str1;    char buf[1024] = {0};    sprintf(buf, "%s%s", str, it.s);    strcpy(str1.s, buf);//友元函数里可以访问私有变量str1.s    return str1;}//重载前++,同上面函数一个道理mystring operator ++(mystring &it){    //str2 = ++str1;    int len = strlen(it.s);    for(int i = 0;i < len; i++)    {        it.s[i]++;//让s的第一个成员char + 1,就是将s[0]对应字符的ASCII码 + 1    }    return it;}mystring operator +(int i, const mystring &it){    //str1 = 10 + str2;    mystring str1;    char buf[1024] = {0};    sprintf(buf, "%d%s", i, it.s);    strcpy(str1.s, buf);    return str1;}void test(int i){    cout << i << endl;}int main(){//    mystring str;//    str << "123";//    test(str);//导致C++编译器自动的配备int()操作符    mystring *p = new mystring;    delete p;//    mystring *p = (mystring *)malloc(sizeof(mystring));//    free(p);    return 0;}int main03(){    mystring str1;    str1 << "hello";    mystring str2;    str2 << "hello";    if ("hello" == str1)    {        cout << "true" << endl;    }else    {        cout << "fasle" << endl;    }    str1[2] = 'a';    //str1("aaaaaaaa");    str1(10);    cout << str1.s << endl;    return 0;}int main02(){    cout << "mystring size =" << sizeof(mystring) << endl;    mystring str1;    str1 =  "hello";    mystring str2;    str2 = " world";    mystring str3;    //str3 = str1 + str2;//对C++编译器来讲,不能识别两个类+是什么含义,要重载+    //str3 = str1 + "aaaaaaaaaaaa";    //str3 = str1 + 100;    //str3 = "AAAAA" + str1;    str3 = 100 + str1;    str3 += "BBBBBB";    str3 << "CCCCC";    char buf[1024] = {0};    str3 >> buf;    str2 = str3++;    str2 = ++str3;    mystring *pstr = new mystring;    delete pstr;    cout << str3.s << endl;    return 0;}int main01(){    mystring str1;    strcpy(str1.s, "hello world");    mystring str2;    str2 = str1;//这个过程不是拷贝构造的过程,只是=号操作,重载了操作符=    //str2.operator =(str1);//和上面直接写=号是一摸一样的    cout << str2.s << endl;    str2 = "test";//C++编译器不能理解把一个字符串赋给一个类是什么含义,要重载=    mystring str3;    str3 = str2 = 100;    //str3 = str2.operator =(100);//上一条语句的等效语法    cout << str2.s << endl;    return 0;}