zoukankan      html  css  js  c++  java
  • 追踪class的成员变量

      今天我所讲的是不通过修改一个class的成员,就能够追踪其成员。方法就是类似C语言中的函数指针,

    比如:int (*foo)(int arg),记住要和另一个指针函数区分开来,类似这样:int *foo(int arg).

      比如我们可以这样声明一个变量和函数:

    int (*pfun)(int arg)=0;
    int fun(int arg);    //这个函数实现随便啦,我就不写了。

    如果我们想利用函数指针操作函数,就和指针变量使用一样:

    pfun=fun;
    
    int result=(*pfun)(123);

    对,很鸡肋也没必要。这是当然,因为我们没用在对的地方。下面我要讲的是利用一个类去call back另一个无关类的成员。

    代码:

     1 #include <iostream>
     2 using namespace std;
     3 template<typename T,typename N>
     4 class Functor{
     5 public:
     6    Functor(T *otherp,N (T::*otherfun)(N arg))
     7    {
     8        mp=otherp;
     9        mfun=otherfun;
    10    } 
    11    virtual N operator()(N arg)
    12    {
    13        return (*mp.*mfun)(arg);
    14    }
    15 private:
    16    N   (T::*mfun)(N arg);
    17    T *mp;
    18 };
    19 class A{
    20 public:
    21     A(int a0):a(a0){}
    22     int traced(int b)
    23     {
    24         cout<<"Trace a="<<a<<",b="<<b<<endl;
    25         return 0;
    26     }
    27 private:
    28     int a;
    29 };
    30 int main()
    31 {
    32     A a(10);
    33     Functor<A,int> trace(&a,&A::traced);
    34     trace(5);
    35     return 0;
    36 }

    第33行把class A的成员函数地址传给了Functor的函数指针,从而能够通过Functor的成员处理A中的成员。

    这里用到了对operator()的重载,可以换成别的函数处理Functor的函数指针

    (不处理也行,但是函数指针很绕人,不直观),像这样:

    View Code
     1 #include <iostream>
     2 using namespace std;
     3 template<typename T,typename N>
     4 class Functor{
     5 public:
     6    Functor(T *otherp,N (T::*otherfun)(N arg))
     7    {
     8        mp=otherp;
     9        mfun=otherfun;
    10    } 
    11    virtual N out(N arg)         //改动
    12    {
    13        return (*mp.*mfun)(arg); 
    14    }
    15 private:
    16    N   (T::*mfun)(N arg);
    17    T *mp;
    18 };
    19 class A{
    20 public:
    21     A(int a0):a(a0){}
    22     int traced(int b)
    23     {
    24         cout<<"Trace a="<<a<<",b="<<b<<endl;
    25         return 0;
    26     }
    27 private:
    28     int a;
    29 };
    30 int main()
    31 {
    32     A a(10);
    33     Functor<A,int> trace(&a,&A::traced);
    34     trace.out(5);      //改动
    35     return 0;
    36 }

    C++确实复杂,但是我们如果利用好,复杂就是强大。

  • 相关阅读:
    使用Jenkins进行android项目的自动构建(3)
    使用Jenkins进行android项目的自动构建(2)
    使用Jenkins进行android项目的自动构建(1)
    testlink 从1.8.5 升级到 1.9.8
    779. 第K个语法符号(Leetcode)
    687. 最长同值路径(Leetcode)(递归+树)
    116. 飞行员兄弟(Acwing)(递归+位运算)
    95. 费解的开关(Acwing)(分析+递推)
    Java遇到输入速度瓶颈时的解决办法
    92. 递归实现指数型枚举(Acwing)(递归)
  • 原文地址:https://www.cnblogs.com/wuchaofan/p/2992812.html
Copyright © 2011-2022 走看看