商業(yè)源碼熱門下載www.html.org.cn
很多情況下,我們需要一個singleton窗體,比如,任務管理器就可以是windows應用系統(tǒng)中的一個singleton,于是我們這樣做:在窗體類的實現(xiàn)中添加一個靜態(tài)指向單件的成員,提供一個靜態(tài)的createinstance方法,當?shù)谝淮握{用此方法時創(chuàng)建單件。另外還要處理closing事件,以使點擊窗體右上角的“×”時,隱藏窗體。每次需要實現(xiàn)一個單件窗體時都要這么做,于是我決定寫一個基類isingletondisplayer,一個窗體不用作任何改變,只需要將原來的基類form改為isingletondisplayer就變成一個singleton窗體,這就很方便了。先給出在vs2003中的實現(xiàn)。public class isingletondisplayer : form  //從form繼承
 {
  private static isingletondisplayer singleton = null ;
  private static bool toclean = false ;
  protected isingletondisplayer()
  {
   this.closing += new system.componentmodel.canceleventhandler(isingletondisplayer_closing);
  }
#region static for singleton
  #region getsingleton
  public static isingletondisplayer getsingleton()
  {
   if(isingletondisplayer.singleton != null)
   {
    isingletondisplayer.singleton.visible = true ;
   }
   return isingletondisplayer.singleton ;
  }
#endregion
#region recreatesingleton
  //formonui存在是因為窗體只能在主線程(ui線程)中創(chuàng)建。
  public static void recreatesingleton(type targettype ,object[] args , form formonui)
  {
   type suptype = typeof(isingletondisplayer) ;
   if(! suptype.isassignablefrom(targettype))
   {
    throw new exception("target type is not derived from isingletondisplayer !") ;
   }
   if(formonui.invokerequired)
   {
    object[] paras = {targettype ,args ,formonui} ;
    formonui.invoke(new cbackcreateform(isingletondisplayer.recreatesingleton) ,paras) ;
   }
   else
   {
    try
    {
     isingletondisplayer.toclean = false ;
     isingletondisplayer.singleton  = (isingletondisplayer)activator.createinstance(targettype ,args) ;
     isingletondisplayer.singleton.visible = false ;
    }
    catch(exception ee)
    {
     throw ee ;
    }
   }
  }
  #endregion
  #region destroysingleton
  public static void destroysingleton()
  {
   isingletondisplayer.toclean = true ;
   if(isingletondisplayer.singleton != null)
   {
    isingletondisplayer.singleton.close() ;
    isingletondisplayer.singleton = null ;
   }
  }
  #endregion
#endregion
  #region isingletondisplayer_closing
  private void isingletondisplayer_closing(object sender, system.componentmodel.canceleventargs e)
  {
   if(! isingletondisplayer.toclean)
   {
    this.visible = false ;
    e.cancel = true ;
    return ;
   }
  }
  #endregion
 }
internal delegate void cbackcreateform(type targettype ,object[] args , form formonui) ;
  * 使用方法:
  * 如果一個displayer需要以singleton模式呈現(xiàn),那么可以先以常規(guī)的方式設計displayer,設計過程中不需要涉及任何與單件
  * 相關的東西。設計完后,只要將displayer的基類由form改為isingletondisplayer即可。接下來即可以單件的模式使用displayer了。
  * 
  * 如:
  * public class appserversinfoform2 : isingletondisplayer{}
  * object[] args = {obj} ;
  * isingletondisplayer.recreatesingleton(typeof(appserversinfoform2) ,args ,formonui) ;
    
 
上面的實現(xiàn)很容易理解,但是上面的實現(xiàn)有一個弊病,因為所有的單件窗體都要公用一個靜態(tài)的isingletondisplayer singleton 成員,所以一個應用程序中只能有一個單件繼承自isingletondisplayer。/ 在vs2005中可以使用泛型突破此限制。
下面在看看在vs2005中的實現(xiàn)。
 public class isingletondisplayer<t> : form
 {
  private static isingletondisplayer<t> singleton = null ;
  private static bool toclean = false ;
  protected isingletondisplayer()
  {
   this.closing += new system.componentmodel.canceleventhandler(isingletondisplayer_closing);
  }
  public static isingletondisplayer<t> getsingleton()
  {
   if(isingletondisplayer<t>.singleton != null)
   {
    isingletondisplayer<t>.singleton.visible = true ;
   }
   return isingletondisplayer<t>.singleton ;
  }
  public static void recreatesingleton(type targettype ,object[] args , form formonui)
  {
   type suptype = typeof(isingletondisplayer) ;
   if(! suptype.isassignablefrom(targettype))
   {
    throw new exception("target type is not derived from isingletondisplayer<t> !") ;
   }
   if(formonui.invokerequired)
   {
    object[] paras = {targettype ,args ,formonui} ;
    formonui.invoke(new cbackcreateform(isingletondisplayer<t>.recreatesingleton) ,paras) ;
   }
   else
   {
    try
    {
     isingletondisplayer<t>.toclean = false ;
     isingletondisplayer<t>.singleton  = (isingletondisplayer<t>)activator.createinstance(targettype ,args) ;
     isingletondisplayer<t>.singleton.visible = false ;
    }
    catch(exception ee)
    {
     throw ee ;
    }
   }
  }
  public static void destroysingleton()
  {
   isingletondisplayer<t>.toclean = true ;
   if(isingletondisplayer<t>.singleton != null)
   {
    isingletondisplayer<t>.singleton.close() ;
    isingletondisplayer<t>.singleton = null ;
   }
  } 
  
  private void isingletondisplayer_closing(object sender, system.componentmodel.canceleventargs e)
  {
   if(! isingletondisplayer<t>.toclean)
   {
    this.visible = false ;
    e.cancel = true ;
    return ;
   }
  }
 
    }
 
internal delegate void cbackcreateform(type targettype ,object[] args , form formonui) ;
    如:
    public class appserversinfoform2 : isingletondisplayer<appserversinfoform2>{}
    object[] args = {obj} ;
    isingletondisplayer<appserversinfoform2>.recreatesingleton(typeof(appserversinfoform2) ,args ,this) ;
這樣每個單件都有自己的靜態(tài)實例,就不會相互干擾了。
如果你有更好的實現(xiàn)方法,歡迎和我討論
新聞熱點
疑難解答