混型

来源:互联网 发布:文华财经 mac 编辑:程序博客网 时间:2024/06/05 17:24

      混型随着时光的飞逝已经被赋予了不同的意味,但是混型的基本概念是他能够让多个类产生一个能代表所有类型的混型,(俺是这样理解的,产生一个类,他能够给具有被混合的所有类型的能力),这往往是你在一次做的东西,可能会使使用起来集合中的类型变得比较简单。

      混型中的一个价值就是它能够跨越多个类使用特性和行为的能力。假如你想改变混型中的某些东西,那些改变将被应用在所有类中混型被用到的东西。正因为此,混型颇有AOP的味道,面向方面编程常被用来解决混型的问题。

      强大的参数记忆功能使C++的多重继承可以被用作混型。但是,一个比较有趣且优雅的方式实现混型就是使用参数类型,这样的话混型就是能一个类他继承自本身的类型的参数。在C++中,你能够很容易创建混型因为C++能够记住模板的参数类型。

      下面是C++的例子带有两个混型:一个允许你参杂时间戳,另一个允许你参杂每一个实例的序列号:

  #include<string>

  #include<ctime>

  #include<iostream>

 using namespace std;

template<class T> class TimeStamped:public T{

   long timeStamp;

 public:

    TimeStamped(){timeStamp = time(0);}

    long getStamp(){return timeStamp}

};

template<class T> class SerialNumbered: public T{

   long serialNumer;

   static long counter;

 public:

    SerialNumbered(){serialNumber = counter++;}

    long getSerialNumber(){return serialNumber;}

};

//Define and initialize the static storage:

template<class T> long SerialNumber<T>::counter = 1;

class Basic{

   string value;

  public:

     void set(string val){value=val;}

     string get(){return value;}

};

int main(){

   TimeStamped<SerialNumbered<Basic>>  mixin1,mixin2;

   mixin1.set("test string 1");

   mixin2.set("test string 2");

   cout<<mixin1.get()<<"  "<<mixin1.getStamp()<<"   "<<mixin1.getSerialNumber()<<endl;

   cout<<mixin2.get()<<"  "<<mixin2.getStamp()<<"   "<<mixin2.getSerialNumber()<<endl;

}

在main方法中,mixin1和mixin2中含有了混合类型中的全部方法。你可能会想混型作为一个方法映射类到新的子类。可现在你看如果用它的话会显得多么琐碎,现在你基本上可以说“你看,这就是我想要的”,只需下面的代码:

TimeStamped<SerialNumbered<Basic>> mixin1,mixin2;

不太走运的是,Java中的泛型不能够如此。擦除会忘掉积累的类型,所以泛型类不能直接继承泛型参数的类型。

一个一般会被推荐的解决方案是用接口实现类似混型的效果:

interface TimeStamped{long getStamp();}

class TimeStampedImp implements TimeStamped{

   private final long timeStamp;

   public TimeStampedImp(){

       timeStamp = new Date().getTime(); 

   }

   public long getStamp(){return timeStamp;}

}

interface SerialNumbered{ long getSerialNumber();}

class SerialNumberedImp implements SerialNumbered{

    private static long counter = 1;

    private final long serialNumber = counter++;

    public long getSerialNumber(){return serialNumber;}

}

interface Basic{

   public void set(String val);

   public String get();

}

class BasicImp implements Basic{

   private String value;

   public void set(String val){value = val;}

   public String get(){return value;}

}

class Mixin extends BasicImp implements TimeStamped,SerialNumbered{

   private TimeStamped timeStamp = new TimeStampedImp();

   private SerialNumbered serialNumber = new SerialNumeredImp();

   public long getStamp(){return timeStamp.getStamp();}

   public long getSerialNumber(){return serialNumber.getSerialNumber();

  }

}

public class Mixins{

   public static void main(String[] args){

    Mixin mixin1 =new Mixin(),mixin2 = new Mixin();

    mixin1.set("test string1");

    mixin2.set("test string2");

    System.out.println(mixin1.get()+"  "+mixin1.getStamp()+"  "+mixin1.getSerialNumber());

    System.out.println(mixin2.get()+"  "+mixin2.getStamp()+"  "+mixin2.getSerialNumber());

  }

}

Mixin基本上用了委托或者叫做(代理),所以每一个混型类型都要求被委托类中的字段,你必须在混型类中写下所有的必须的方法以供调用。这个例子使用了小小的一些类,但是混型的内容越复杂,代码量会急剧增加的。

原创粉丝点击