MVC框架下单例模式挑奇偶(界面与控制台view模式)


一.何为单例模式

单例模式,也叫单子模式,是一种常用的软件设计模式。在应用这个模式时,单例对象的类必须保证只有一个实例存在。许多时候整个系统只需要拥有一个的全局对象,这样有利于我们协调系统整体的行为。比如在某个服务器程序中,该服务器的配置信息存放在一个文件中,这些配置数据由一个单例对象统一读取,然后服务进程中的其他对象再通过这个单例对象获取这些配置信息。这种方式简化了在复杂环境下的配置管理。(选自维基百科)
通常单例模式在Java语言中,有两种构建方式:
懒汉方式。指全局的单例实例在第一次被使用时构建。
饿汉方式。指全局的单例实例在类装载时构建。
下面是自己对两种方式的优缺点辨析:懒汉方式由于是在使用时才创建示例,因为类加载较快,但是懒汉方式在多线程情况下不能使用(所以笔者的懒汉代码示例是变种懒汉),而饿汉方式则没有线程不安全的情况,在装载类时就创建实例,但是其效率较之于懒汉模式就比较低。

二.为何用使用单例模式

1 .首先,只需要创建一个实例对象,占用内存较少。
2.能避免存在多个实例影响程序逻辑错误的场合。

三.代码示例(界面与 控制台两种视图模式)

下面是加双锁以确保线程安全的懒汉模式(同时也是MVC框架的Controller):
import javax.swing.JFrame;
public class Singleton {
	 private static volatile Singleton INSTANCE=null;
		private Num NUM;
		private Numview1 VIEW1;
		private Numview2 VIEW2;
		private int mode;//视图模式选择
		 private Singleton(){};
	public static Singleton getinstance()
		 {
		 if(INSTANCE==null)
		 {
		 synchronized(Singleton.class)
		 {
		 if(INSTANCE==null)
		 INSTANCE=new Singleton();
		 }
		 }
		 return INSTANCE;
		 }
	public void setMode(int i)//设置视图模式,1为界面,2为控制台
	{
		mode=i;
	}
	
	public void CreateNum(int num)
		{
			NUM=new Num(num);
		}
	 public int getNum()
	 {
		 return NUM.getNum();
	 }
	 public String getAttribute()
	 {
		 return NUM.getAttribute();
	 }
	 public void Judge()
	 {
		 NUM.Judge();
	 }
	 public void ShowView()
	 {
		 switch(mode){
		 case 1:
		 {
			 VIEW1=new Numview1(this);
		     VIEW1.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		     VIEW1.setSize(450,120);
		     VIEW1.setVisible(true);
		     break;
		 }
		 case 2:
		 {
			 VIEW2=new Numview2(this);
			 VIEW2.show();
			 break;
		 }
		 default :System.out.println("设置视图模式错误");
	 }
	 }
}


普通饿汉模式(只写了改变和获取实例这部分即可,其他Controller部分与懒汉模式一样)
public class Singleton {
 	private static Singleton INSTANCE = new Singleton();//静态私有成员,已初始化
private static volatile Singleton INSTANCE=null;
 private Num NUM;
 private Numview1 VIEW1;
 private Numview2 VIEW2;	private int mode;//视图模式选择
private Singleton(){};
public static Singleton getinstance()//返回唯一实例
 { 
return INSTANCE; 
}
}

下面是MVC的model,也就是数这个对象
public class Num {
 private int num;
 private String att;
 public Num(int i)
 {
 	num=i;
 	att=new String("这是一个数");
 }
 public void setNum(int i)
 {
	 num=i;
 }
 public int getNum()
 {
	 return num;
 }
 public String getAttribute()
 {
	 return att;
 }
 public void Judge()
 {
	 if(num%2==0)
		 att="这是一个偶数";
	 else
		 att="这是一个奇数";
 }
}

View模块

视图模式1(界面)
import java.awt.Container;
import javax.swing.JFrame;
import java.awt.FlowLayout;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.*;
public class Numview1 extends JFrame  {
	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	private Singleton CONTROL;
	public Numview1(Singleton Con)
	{
		super("奇偶判断");
		CONTROL=Con;
		Container c=getContentPane();//创建面板
		c.setLayout(new FlowLayout());
		JTextField DisNum=new JTextField("数字:",8);
		DisNum.setEditable(false);
		JTextField Num=new JTextField(8);//用于输入数字
		Num.setEditable(true);
		JButton Judge=new JButton("判断");
		JTextField Display=new JTextField(8); //显示判断结果
		Display.setEditable(false);	
		c.add(DisNum);
		c.add(Num);
		c.add(Judge);
		c.add(Display);
		Judge.addMouseListener(new MouseListener(){
			public void mouseClicked(MouseEvent e)
			{
				String _num=Num.getText();
				CONTROL.CreateNum(Integer.parseInt(_num));
				CONTROL.Judge();
				Display.setText(Con.getAttribute());
			}
			public void mouseEntered(MouseEvent e) {			
			}
			public void mouseExited(MouseEvent e) {
			}
			public void mousePressed(MouseEvent e) {
			}
			public void mouseReleased(MouseEvent e) {
			} 
		});
			
	}
}


视图模块2(控制台)
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class Numview2 {
	private Singleton CONTROL;
	public Numview2(Singleton Con){
		CONTROL=Con;
	}
	public void show(){
      BufferedReader in=new BufferedReader(new InputStreamReader(System.in));  
      String _num;  
      try  
      {  
          do{  
              _num=in.readLine();  
              if(Integer.parseInt(_num)!=-1)  
              {  
                  CONTROL.CreateNum(Integer.parseInt(_num));//对对象进行相关处理  
                  CONTROL.Judge();//  判断并设置属性
                  System.out.println(CONTROL.getAttribute());
              }  
              }while(Integer.parseInt(_num)!=-1);  
          System.out.println("结束");  
          }  
      catch(IOException e)  
      {  
          System.out.println(e.getMessage());  
          e.printStackTrace();  
      }  
  }  
}


四.结果

视图1(界面)




视图2(控制台)



五.总结:

看了几篇关于单例模式的博客,对单例模式有了大概的了解,单线程用懒汉模式较好,如果在多线程的情况下,就需要通过加锁等方式来保证线程安全,饿汉模式的话虽然安全,但由于是一开始就创建了实例,可能造成内存浪费,然后就是如何将单例与MVC模式相结合,笔者会在后面的博客里再进行关于对MVC理解的探讨。由于是菜鸟一只,如有什么不对的地方,还请不吝赐教,请在评论下留言。


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值