美文网首页
C++ 重载运算符

C++ 重载运算符

作者: 秋水涟漪 | 来源:发表于2016-09-15 15:44 被阅读0次

    -> arrow operator

    参考资料

    stackoverflow 最高票翻译

    • ->
      它必须被定义为非静态成员函数(原因是需要this指针), 且没有参数. 它的返回值 被用来 调用 该返回值的成员
      如果该返回值是另一个类类型, 而非指针, 那么就会继续调用该类类型的operator->函数. 这种行为被称为"drill-down behavior". 直到最后一个返回的是指针为止.
    struct client
        { int a; };
    
    struct proxy {
        client *target;
        client *operator->() const
            { return target; }
    };
    
    struct proxy2 {
        proxy *target;
        proxy &operator->() const
            { return * target; }
    };
    
    void f() {
        client x = { 3 };
        proxy y = { & x };
        proxy2 z = { & y };
    
        std::cout << x.a << y->a << z->a; // print "333"
    }
    

    ->* .* 和 .

    • ->*
      这个运算符并不特殊,和普通的二目运算符相似, 也没有必须为非静态成员的限制.
      若为非静态成员, 参考Thinking in c++ , 专门为类设计了存放函数的类. 该类是一个类函数, ->* 在返回处 调用它的构造函数, 执行时会把目标函数的参数传给该类的迭代器的operator()

    • .* 和 .
      这两个不能重载

    #include <iostream>
    using namespace std;
    class AB {
    public:
        int a;
        int b;
        typedef void (AB::*action)() const;
        AB():a(1),b(2){}
        AB(const int&x, const int &y):a(x),b(y){}
        void func_1() const {
            cout <<"AB::func_1()"<<endl;
        }
        void func_2() const {
            cout <<"AB::func_2()"<<endl;
        }
    };
    
    class ABset {
        typedef AB* ABP;
        AB ab[20];
    public:
        friend class absiterator;
        typedef class absiterator iterator;
        ABset(){
            for(int i=0;i<20;i++){
                ab[i].a = i;
                ab[i].b = i*2;
            }
        }
        ABP begin(){
            return &(ab[0]);
        }
    };
    class absiterator {
        typedef AB& ABRef;
        typedef AB* ABP;
        typedef AB::action ABACT;
        typedef ABP & ABPRef;
        typedef absiterator __Self;
        ABP abptr;
    public:
        
        absiterator(ABP abp):abptr(abp){}
        absiterator():abptr(NULL){}
        
        ABRef operator*(){
            return *abptr;
        }
        ABP operator->(){
            return abptr;
        }
        ABPRef operator=(AB *abp){
            abptr = abp;
            return abptr;
        }
        ABPRef operator+(int n){
            abptr += n;
            return abptr;
        }
    };
    struct Dog{
        Dog(){cout <<"\nDog()"<<endl;}
        int run(int a){
            cout <<"run "<<a<<endl;
            return a;
        }
        int sleep(int b){
            cout <<"sleep "<<b<<endl;
            return b;
        }
        int eat(int c){
            cout <<"eat "<<c<<endl;
            return c;
        }
        typedef int (Dog::*action)(int); 
        class FuncIter {
            Dog* ptr;
            Dog::action act;
        public:
            FuncIter(Dog* wp, action ai): ptr(wp), act(ai) {
                cout <<"construction FuncIter"<<endl;
            } 
            int operator()(int a){
                cout <<"operator()"<<endl;
                return (ptr->*act)(a);
            }
         };
        class FuncIter operator->*(action ai){
            cout <<"operator->*"<<endl;
            return FuncIter(this,ai);
        }
    };
    
    int main ()
    {
        ABset ax;
        ABset::iterator ai = ax.begin();
        //AB::action act = &AB::func_2;
        ai = ai+2;
        cout <<ai->a<<endl;
        cout <<(*ai).b<<endl;
        ai->func_1();
            
        Dog dg;
        Dog::action dact = &Dog::run;
        (dg->*dact)(3);
        return 0;
    }
    

    相关文章

      网友评论

          本文标题:C++ 重载运算符

          本文链接:https://www.haomeiwen.com/subject/jhsbettx.html