精华内容
下载资源
问答
  • JAVA设计模式之单例模式

    万次阅读 多人点赞 2014-04-16 06:51:34
     java中单例模式是一种常见的设计模式,单例模式的写法有好几种,这里主要介绍三种:懒汉式单例、饿汉式单例、登记式单例。  单例模式有以下特点:  1、单例类只能有一个实例。  2、单例类必须自己创建自己的...

    本文继续介绍23种设计模式系列之单例模式。

    概念:
      java中单例模式是一种常见的设计模式,单例模式的写法有好几种,这里主要介绍三种:懒汉式单例、饿汉式单例、登记式单例。
      单例模式有以下特点:
      1、单例类只能有一个实例。
      2、单例类必须自己创建自己的唯一实例。
      3、单例类必须给所有其他对象提供这一实例。
      单例模式确保某个类只有一个实例,而且自行实例化并向整个系统提供这个实例。在计算机系统中,线程池、缓存、日志对象、对话框、打印机、显卡的驱动程序对象常被设计成单例。这些应用都或多或少具有资源管理器的功能。每台计算机可以有若干个打印机,但只能有一个Printer Spooler,以避免两个打印作业同时输出到打印机中。每台计算机可以有若干通信端口,系统应当集中管理这些通信端口,以避免一个通信端口同时被两个请求同时调用。总之,选择单例模式就是为了避免不一致状态,避免政出多头。


    一、懒汉式单例

     

    //懒汉式单例类.在第一次调用的时候实例化自己 
    public class Singleton {
        private Singleton() {}
        private static Singleton single=null;
        //静态工厂方法 
        public static Singleton getInstance() {
             if (single == null) {  
                 single = new Singleton();
             }  
            return single;
        }
    }

     

    Singleton通过将构造方法限定为private避免了类在外部被实例化,在同一个虚拟机范围内,Singleton的唯一实例只能通过getInstance()方法访问。

    (事实上,通过Java反射机制是能够实例化构造方法为private的类的,那基本上会使所有的Java单例实现失效。此问题在此处不做讨论,姑且掩耳盗铃地认为反射机制不存在。)

    但是以上懒汉式单例的实现没有考虑线程安全问题,它是线程不安全的,并发环境下很可能出现多个Singleton实例,要实现线程安全,有以下三种方式,都是对getInstance这个方法改造,保证了懒汉式单例的线程安全,如果你第一次接触单例模式,对线程安全不是很了解,可以先跳过下面这三小条,去看饿汉式单例,等看完后面再回头考虑线程安全的问题:

     

    1、在getInstance方法上加同步

     

    public static synchronized Singleton getInstance() {
             if (single == null) {  
                 single = new Singleton();
             }  
            return single;
    }

     

     

     

    2、双重检查锁定

     

    public static Singleton getInstance() {
            if (singleton == null) {  
                synchronized (Singleton.class) {  
                   if (singleton == null) {  
                      singleton = new Singleton(); 
                   }  
                }  
            }  
            return singleton; 
        }

     

    3、静态内部类

     

    public class Singleton {  
        private static class LazyHolder {  
           private static final Singleton INSTANCE = new Singleton();  
        }  
        private Singleton (){}  
        public static final Singleton getInstance() {  
           return LazyHolder.INSTANCE;  
        }  
    }  

    这种比上面1、2都好一些,既实现了线程安全,又避免了同步带来的性能影响。

     

     

     

     

     

     

    二、饿汉式单例

     

    //饿汉式单例类.在类初始化时,已经自行实例化 
    public class Singleton1 {
        private Singleton1() {}
        private static final Singleton1 single = new Singleton1();
        //静态工厂方法 
        public static Singleton1 getInstance() {
            return single;
        }
    }

    饿汉式在类创建的同时就已经创建好一个静态的对象供系统使用,以后不再改变,所以天生是线程安全的。

     

     

     

     

    三、登记式单例(可忽略)

    //类似Spring里面的方法,将类名注册,下次从里面直接获取。
    public class Singleton3 {
        private static Map<String,Singleton3> map = new HashMap<String,Singleton3>();
        static{
            Singleton3 single = new Singleton3();
            map.put(single.getClass().getName(), single);
        }
        //保护的默认构造子
        protected Singleton3(){}
        //静态工厂方法,返还此类惟一的实例
        public static Singleton3 getInstance(String name) {
            if(name == null) {
                name = Singleton3.class.getName();
                System.out.println("name == null"+"--->name="+name);
            }
            if(map.get(name) == null) {
                try {
                    map.put(name, (Singleton3) Class.forName(name).newInstance());
                } catch (InstantiationException e) {
                    e.printStackTrace();
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                } catch (ClassNotFoundException e) {
                    e.printStackTrace();
                }
            }
            return map.get(name);
        }
        //一个示意性的商业方法
        public String about() {    
            return "Hello, I am RegSingleton.";    
        }    
        public static void main(String[] args) {
            Singleton3 single3 = Singleton3.getInstance(null);
            System.out.println(single3.about());
        }
    }

     登记式单例实际上维护了一组单例类的实例,将这些实例存放在一个Map(登记薄)中,对于已经登记过的实例,则从Map直接返回,对于没有登记的,则先登记,然后返回。 

    这里我对登记式单例标记了可忽略,我的理解来说,首先它用的比较少,另外其实内部实现还是用的饿汉式单例,因为其中的static方法块,它的单例在类被装载的时候就被实例化了。

     

    饿汉式和懒汉式区别

    从名字上来说,饿汉和懒汉,

    饿汉就是类一旦加载,就把单例初始化完成,保证getInstance的时候,单例是已经存在的了,

    而懒汉比较懒,只有当调用getInstance的时候,才回去初始化这个单例。

    另外从以下两点再区分以下这两种方式:

     

    1、线程安全:

    饿汉式天生就是线程安全的,可以直接用于多线程而不会出现问题,

    懒汉式本身是非线程安全的,为了实现线程安全有几种写法,分别是上面的1、2、3,这三种实现在资源加载和性能方面有些区别。


     

    2、资源加载和性能:

    饿汉式在类创建的同时就实例化一个静态对象出来,不管之后会不会使用这个单例,都会占据一定的内存,但是相应的,在第一次调用时速度也会更快,因为其资源已经初始化完成,

    而懒汉式顾名思义,会延迟加载,在第一次使用该单例的时候才会实例化对象出来,第一次调用时要做初始化,如果要做的工作比较多,性能上会有些延迟,之后就和饿汉式一样了。

    至于1、2、3这三种实现又有些区别,

    第1种,在方法调用上加了同步,虽然线程安全了,但是每次都要同步,会影响性能,毕竟99%的情况下是不需要同步的,

    第2种,在getInstance中做了两次null检查,确保了只有第一次调用单例的时候才会做同步,这样也是线程安全的,同时避免了每次都同步的性能损耗

    第3种,利用了classloader的机制来保证初始化instance时只有一个线程,所以也是线程安全的,同时没有性能损耗,所以一般我倾向于使用这一种。

     

    什么是线程安全?

    如果你的代码所在的进程中有多个线程在同时运行,而这些线程可能会同时运行这段代码。如果每次运行结果和单线程运行的结果是一样的,而且其他的变量的值也和预期的是一样的,就是线程安全的。

    或者说:一个类或者程序所提供的接口对于线程来说是原子操作,或者多个线程之间的切换不会导致该接口的执行结果存在二义性,也就是说我们不用考虑同步的问题,那就是线程安全的。

     

    应用

    以下是一个单例类使用的例子,以懒汉式为例,这里为了保证线程安全,使用了双重检查锁定的方式:

     

    public class TestSingleton {
    	String name = null;
    
            private TestSingleton() {
    	}
    
    	private static volatile TestSingleton instance = null;
    
    	public static TestSingleton getInstance() {
               if (instance == null) {  
                 synchronized (TestSingleton.class) {  
                    if (instance == null) {  
                       instance = new TestSingleton(); 
                    }  
                 }  
               } 
               return instance;
    	}
    
    	public String getName() {
    		return name;
    	}
    
    	public void setName(String name) {
    		this.name = name;
    	}
    
    	public void printInfo() {
    		System.out.println("the name is " + name);
    	}
    
    }

    可以看到里面加了volatile关键字来声明单例对象,既然synchronized已经起到了多线程下原子性、有序性、可见性的作用,为什么还要加volatile呢,原因已经在下面评论中提到,

    还有疑问可参考http://www.iteye.com/topic/652440
    和http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html

     

     

     

    public class TMain {
    	public static void main(String[] args){
    		TestStream ts1 = TestSingleton.getInstance();
    		ts1.setName("jason");
    		TestStream ts2 = TestSingleton.getInstance();
    		ts2.setName("0539");
    		
    		ts1.printInfo();
    		ts2.printInfo();
    		
    		if(ts1 == ts2){
    			System.out.println("创建的是同一个实例");
    		}else{
    			System.out.println("创建的不是同一个实例");
    		}
    	}
    }
    

     运行结果:

    结论:由结果可以得知单例模式为一个面向对象的应用程序提供了对象惟一的访问点,不管它实现何种功能,整个应用程序都会同享一个实例对象。

    对于单例模式的几种实现方式,知道饿汉式和懒汉式的区别,线程安全,资源加载的时机,还有懒汉式为了实现线程安全的3种方式的细微差别。

    更多设计模式:23种设计模式系列

    作者:jason0539

    博客:http://blog.csdn.net/jason0539(转载请说明出处)

    展开全文
  • Java后台实现调用外部接口

    千次阅读 2018-12-04 18:52:42
    Java调用外部接口的方法,最终返回接口return的信息 代码如下: public class demo{ private string line; String strURL = "这里是你要调用的接口地址"; URL url = new URL(strURL); ...

    Java调用外部接口的方法,最终返回接口return的信息
    代码如下:
    public class demo{

      private string line;
       String strURL = "这里是你要调用的接口地址";
        URL url = new URL(strURL);
        HttpURLConnection httpConn = (HttpURLConnection)url.openConnection();
       httpConn.setRequestMethod("GET");
        httpConn.connect();
        BufferedReader reader = new BufferedReader(new InputStreamReader(httpConn.getInputStream()));
        StringBuffer buffer = new StringBuffer();
        while ((line = reader.readLine()) != null) {
            buffer.append(line);
        }
        reader.close();
        httpConn.disconnect();
        System.out.println(buffer.toString());
    

    }

    接口return的值就是buffer.toString();

    展开全文
  • java外部接口与内部接口的使用

    万次阅读 2016-03-20 22:35:44
    晚上写连连看排行榜的时候,查看...具体来说,就是你只实现了外部接口,那么就必须实现外部接口的所有方法;而要用内部的接口的方法只能实现内部接口。 直接将步骤吧: 1、新建一个Java项目 2、新建接口如下:

    晚上写连连看排行榜的时候,查看SharedPreferences源码时发现了一个惊天的秘密。

    为什么一个接口中可以再定义接口呢?

    后来自己网上查找了下资料,然后自己操作了一遍。这个内部类真好用,推荐大家开发中可以用。具体来说,就是你只实现了外部接口,那么就必须实现外部接口的所有方法;而要用内部的接口的方法只能实现内部接口。

    直接将步骤吧:

    1、新建一个Java项目

    2、新建接口如下:

    public interface OuterInterface {//外部接口
    public void showOuter();
    public void showOuter(int a);
    public interface InnerInterface{//内部接口
    public void showInner();
    public void showInner(String str);
    }
    }

    3、新建一个非抽象类(普通类)实现接口如下:

    /**
     * 个人总结:
     * 回顾下接口与类的关系: 1、普通类实现了接口,那么就必须实现接口中的所有方法
     *  2、那么反过来没有实现接口中的方法的类就是抽象类
     *  3、一个类可以实现多个接口
     * 
     * 这里用内部类的好处就是:   1、当你只实现外部接口,那么只需实现外部接口的方法即可(内部接口是调不到的)。
     * (非抽象了的情况下) 2、而实现内部接口的方式是“外部接口.内部接口”,那么就可以实现内部接口的方法了(看下面的例子)
     * 
     * */
    public class TestClass implements OuterInterface,OuterInterface.InnerInterface{//定义一个测试类实现来实现接口
    @Override
    public void showOuter() {
    // TODO Auto-generated method stub

    }
    @Override
    public void showOuter(int a) {
    // TODO Auto-generated method stub

    }
    /***************************************/
    @Override
    public void showInner() {
    // TODO Auto-generated method stub

    }
    @Override
    public void showInner(String str) {
    // TODO Auto-generated method stub

    }
    }

    4、看完了自己动手操作遍熟悉下吧!

    展开全文
  • Java接口 和 接口

    千次阅读 多人点赞 2015-06-20 16:00:49
    1.定义: Java接口是一系列方法的声明,是一些方法特征的集合,一个接口只有方法的特征没有方法的实现,因此这些方法可以在不同的地方被不同的类实现,而这些实现可以具有不同的行为(功能)。两种含义:一,Java...

        1.定义:      Java接口是一系列方法的声明,是一些方法特征的集合,一个接口只有方法的特征没有方法的实现,因此这些方法可以在不同的地方被不同的类实现,而这些实现可以具有不同的行为(功能)。两种含义:一,Java接口,Java语言中存在的结构,有特定的语法和结构;二,一个类所具有的方法的特征集合,是一种逻辑上的抽象。前者叫做“Java接口”,后者叫做“接口”。

        2.功能:   在Java语言规范中,一个方法的特征仅包括方法的名字,参数的数目和种类,而不包括方法的返回类型,参数的名字以及所抛出来的异常。在Java编译器检查方法的重载时,会根据这些条件判断两个方法是否是重载方法。但在Java编译器检查方法的置换时,则会进一步检查两个方法(分处超类型和子类型)的返还类型和抛出的异常是否相同。

              接口实现和类继承的规则不同,为了数据的安全,继承时一个类只有一个直接父类,也就是单继承,但是一个类可以实现多个接口,接口弥补了类的不能多继承缺点,继承和接口的双重设计既保持了类的数据安全也变相实现了多继承。

             Java接口本身没有任何实现,因为Java接口不涉及表象,而只描述public行为,所以Java接口比Java抽象类更抽象化。但是接口不是类,不能使用new 运算符实例化一个接口。如 x=new comparable(......);//这个是错误来的。但是可以声明接口变量Comparable x; //这是允许的。

             Java接口的方法只能是抽象的和公开的,Java接口不能有构造器,Java接口可以有public、静态的和final属性。即接口中的属性可以定义为 public static final int value=5;

             接口把方法的特征和方法的实现分割开来。这种分割体现在接口常常代表一个角色,它包装与该角色相关的操作和属性,而实现这个接口的类便是扮演这个角色的演员。一个角色由不同的演员来演,而不同的演员之间除了扮演一个共同的角色之外,并不要求其它的共同之处。

       3.使用:两个类中的两个类似的功能,调用他们的类动态的决定一种实现,那他们提供一个抽象父类,子类分别实现父类所定义的方法。
    问题的出现:Java是一种单继承的语言,一般情况下,哪个具体类可能已经有了一个超类,解决是给它的父类加父类,或者给它父类的父类加父类,直到移动到类等级结构的最顶端。这样一来,对一个具体类的可插入性的设计,就变成了对整个等级结构中所有类的修改。
    可插入性
    在一个等级结构中的任何一个类都可以实现一个接口,这个接口会影响到此类的所有子类,但不会影响到此类的任何超类。此类将不得不实现这个接口所规定的方法,而其子类可以从此类自动继承这些方法,当然也可以选择置换掉所有的这些方法,或者其中的某一些方法,这时候,这些子类具有了可插入性(并且可以用这个接口类型装载,传递实现了他的所有子类)。
    我们关心的不是那一个具体的类,而是这个类是否实现了我们需要的接口。
    接口提供了关联以及方法调用上的可插入性,软件系统的规模越大,生命周期越长,接口使得软件系统的灵活性和可扩展性,可插入性方面得到保证。
    类型
    使用Java接口将软件单位与内部和外部耦合起来。使用Java接口不是具体的类进行变量的类型声明,方法的返还类型声明,参量的类型声明,以及数据类型的转换。
    在理想的情况下,一个具体的Java类应当只实现Java接口和抽象Java类中声明的方法,而不应当给多余方法。
    等级结构


    Java接口(以及抽象类)一般用来作为一个类型的等级结构的起点。
    如果一个类已经有了一个主要的超类型,那么通过实现一个接口,这个类可以拥有另一个次要的超类型,这种次要的超类型叫做混合类型。

    展开全文
  • java 后端设计高并发接口总结

    千次阅读 2019-02-27 22:55:43
    如何设置高并发接口一、并发队列的选择二、请求接口的合理设计三、高并发下的数据安全3、1 超发的原因3、2 悲观锁思路3、3 FIFO队列思路3、4 乐观锁思路 一、并发队列的选择 Java的并发包提供了三个常用的并发队列...
  • 基于接口设计原则-java

    千次阅读 2015-12-10 10:09:43
    7种设计坏味道 1.僵化性: 很难对系统进行改动,因为每个改动都会迫使许多对系统其他部分的其它改动。 2.脆弱性:对系统的改动会导致系统中和改动的地方在概念上无关的许多地方出现问题。 3.牢固性:很难解开系统...
  • Java接口详解

    千次阅读 多人点赞 2016-08-03 12:40:22
    Java 8对接口进行了改进,允许在接口中定义默认方法,默认方法可以提供方法实现。一、接口的概念 我们经常在生活中听到接口这个词,比如PCI接口、AGP接口,因此很多人认为接口相当于主板上一个插槽,这其实是一种...
  • Java 对第三方提供通用接口设计

    千次阅读 2020-03-06 11:57:10
    在软件开发中,往往需要给第三方提供接口服务,一般通过SOAP协议或者HTTP协议来传输数据,本文不对SOAP协议进行研究,针对HTTP协议进行对外接口通过设计, 二. 设计 1. 首先系统会创建一个账号:密钥id,密钥...
  • Java接口 详解(一)

    万次阅读 多人点赞 2016-10-06 00:46:42
    一、基本概念接口(Interface),在JAVA编程语言中是一个抽象类型,是抽象方法的集合。接口通常以interface来声明。一个类通过继承接口的方式,从而来继承接口的抽象方法。如果一个类只由抽象方法和全局常量组成,...
  • 《Java核心技术卷I》java接口 笔记

    千次阅读 多人点赞 2021-03-03 21:42:27
    写在最前:本笔记全程参考《Java核心技术卷I》,添加了一些个人的思考和整理 接口 1、接口的概念 接口用来描述类应该做什么,而不指定他们应该怎么做。 接口不是类,而是对希望符合这个接口的类的一组需求。不可以...
  • Java接口回调

    千次阅读 2015-07-14 16:42:04
    Java接口回调1. 关于回调回调机制是一种常见的设计模型,他把工作流内的某个功能,按照约定的接口暴露给外部使用者,为外部使用者提供数据,或要求外部使用者提供数据。软件模块之间总是存在着一定的接口,从调用...
  • Java进阶3 —— 类和接口设计原则

    千次阅读 2017-02-13 16:06:31
    本文是Java进阶课程的第三篇。 本课程的目标是帮你更有效的使用Java。其中讨论了一些高级主题,包括对象的创建、并发、序列化、反射以及其他高级特性。本课程将为你的精通Java的旅程提供帮助。 内容纲要 引言...
  • java中,开发数据接口外部提供服务是很正常的事情,可是在选择技术上犯了难。 我了解的编写接口的方式有: socket编程 servlet webservice http+json 对于上面的四种方式,基本上都能实现我目前的项目需求...
  • Java 接口规范与最佳实践

    千次阅读 2018-11-12 16:21:54
    格式统一:这里涉及很多方面,包括:接口返回类型、命名规则以及参数顺序 在我们所有的API方法中,要么是全是getXYZ()格式,要么全是xyz(),最好不要两种格式都有。 假设我们有方法重载,原始方法接受参数Object...
  • Java设计模式-接口隔离原则

    千次阅读 2019-03-11 08:40:15
    接口隔离原则 【Interface Segregation Principle】   定义1:客户端不应该依赖它不需要的接口;一个类对另一个类的依赖应该建立在最小的接口上(Clients should not be forced to depend upon interfaces that ...
  • Java接口-总结

    千次阅读 2013-09-08 10:39:52
    2、与Java接口相关的设计模式 (1)定制服务模式  设计精粒度的接口,每个Java接口代表相关的一组服务,通过继承来创建复合接口 (2) 适配器模式  当每个系统之间接口不匹配时,用适配器来转换接口 (3) 默认...
  • 什么是Java接口? Java接口是什么? Java接口有什么作用? Java接口的作用是什么? Java Interface有什么用? 面对这些疑惑, 相信刚开始学习Java的小朋友真的不懂 懵圈有没有? 下面听我给你讲讲Java的接口到底是什么? 有...
  • Java 接口和抽象类

    千次阅读 2016-05-15 00:36:20
    介绍Java中的接口和抽象类 Java 接口和抽象类 版本号: 2018/9/29-1(22:40) 文章目录 Java 接口和抽象类 接口(27) Marker Interface functional interface default method 抽象类(18) 接口与抽象类区别(10)...
  • JAVA接口与类型安全

    千次阅读 2006-06-09 12:36:00
    接口的两种含义:一,Java接口,Java语言中存在的结构,有特定的语法和结构;二,一个类所具有的方法的特征集合,是一种逻辑上的抽象。前者叫做“Java接口”,后者叫做“接口”。在Java语言规范中,一个方
  • 在这种情况下,各个对象内部是如何实现自己的对系统设计人员来讲就不那么重要了;而各个对象之间的协作关系则成为系统设计的关键。小到不同类之间的通信,大到各模块之间的交互,在系统设计之初都是要着重考虑的,这...
  • 软件接口设计

    万次阅读 2016-11-26 17:27:47
    软件接口设计 《构建可扩展的Web站点》主要介绍了Web应用程序的概念、体系结构、硬件需求、开发环境的原则及国际化、本地化和Unicode等基本内容,本文是软件接口设计。 AD:51CTO 网+ 第十二期沙龙:大话数据之...
  • 老帖了,但是还是想自己收录一下。最后也把自己对于这个问题的一些粗糙的理解记录下来。   在一个面向对象的系统中,系统的各种功能是由许许多多的不同对象协作完成的。在这种情况下,各个对象内部是如何...面向接口
  • Java高级系列——如何设计类和接口

    万次阅读 2018-01-06 14:27:55
    在本系列文章的这一部分我们将会讨论Java语言提供的基础构件和引进的一些设计规则来帮助大家在项目研发过程中做出最好的设计决策。 确切的讲,我们将会讨论接口(interfaces)和接口默认方法(interfaces with ...
  • 定义:客户端不应该依赖它不需要的接口;一个类对另一个类的依赖应该建立在最小的接口上。 问题由来:类A通过接口I依赖类B,类C通过接口I依赖类D,如果接口I对于类A和类C来说不是最小接口,则类B和类D必须去实现...
  • 高并发接口设计思路

    千次阅读 2018-12-27 16:09:53
    Java的并发包提供了三个常用的并发队列实现,分别是:ArrayBlockingQueue、ConcurrentLinkedQueue 和 LinkedBlockingQueue 。 ArrayBlockingQueue是初始容量固定的阻塞队列,我们可以用来作为数据库模块成功竞拍的...
  • 类和接口Java程序设计语言的核心,也是java语言的基本抽象单位。java语言提供许多强大基本元素,供我们来设计接口。怎么才能设计出更加有用,健壮和灵活的类和接口? 首先区别设计良好的模块与设计不好的模块...
  • Java接口和内部类

    千次阅读 2018-09-20 15:00:16
    与Android事件相关的Java知识主要包括:接口、内部类,下面讲解这些知识点。 1、接口 Java接口主要描述类应该具备什么功能。接口是一种契约机制,描述了相关的类应遵循一定的、统一的格式定义。在Java中,接口...
  • 前言 众所周知,Java是一种面向对象的只允许单继承的语言,这是每个Java程序员从业者都知道定理...我们都知道Java的主要设计者是James Gosling,下面我引用它的一段话来对Java语言进行定义: Java是一种简单的,面...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 174,625
精华内容 69,850
关键字:

外部java接口设计

java 订阅