当前位置: 首页 > news >正文

长春 餐饮 网站建设济南哪里做网站

长春 餐饮 网站建设,济南哪里做网站,公司网址格式怎么写,工商营业执照查询网目录 1 单例模式的程序结构 2 饿汉式单例模式的实现 3 饿汉式线程安全 4 防止反射破坏单例 5 总结 单例模式#xff08;Singleton Pattern#xff09;是 Java 中最简单的设计模式之一。所谓单例就是在系统中只有一个该类的实例#xff0c;并且提供一个访问该实例的全局…        目录 1 单例模式的程序结构 2 饿汉式单例模式的实现 3 饿汉式线程安全 4 防止反射破坏单例 5 总结 单例模式Singleton Pattern是 Java 中最简单的设计模式之一。所谓单例就是在系统中只有一个该类的实例并且提供一个访问该实例的全局访问方法。这种类型的设计模式属于创建型模式它提供了一种创建对象的最佳方式关于单例模式的原理可参考文末的链接文章。 单例的实现分为三个步骤 构造方法私有化。即不能在类外实例化只能在类内实例化。在本类中完成自身的初始化自己创建本类的实例且是唯一的实例。在本类中提供给外部获取实例的方式提供访问该实例的全局静态方法getInstance()来获取该类的唯一实例引用。单例模式的特点从系统启动到终止整个过程只会产生一个实例。因为单例提供了唯一实例的全局访问方法所以它可以优化共享资源的访问避免对象的频繁创建和销毁从而可以提高性能。单例模式常见的应用场景如下Windows任务管理器、数据库连接池、Java中的Runtime、Spring中Bean的默认生命周期等。 1 单例模式的程序结构 单例模式简化后的类图如下所示 类图显示了该类的一个私有静态成员变量、一个公有静态方法又叫静态成员函数以及一个私有的构造函数。虽然这是简化后的结构但也是单例模式的主要结构。顺便说一下这个类图只是个简化后的结构该类通常还会有其它的非静态的成员变量和方法当获取到该类的唯一实例后就在该实例上调用这些其它方法来执行该类提供的功能。 私有的构造函数保证只能在类内部实例化静态成员变量用来保存该类的唯一实例该静态成员变量必须是private的以防止用户可以直接访问到它。如果用户想要访问该单例类的唯一实例它只能调用该类的静态方法getInstance。 注意static静态成员变量、静态方法的使用。从语法上来说创建的单例类是不允许被其他程序用new来创建该对象的所以只能将这个单例类中的方法定义成静态的而静态方法又不能去访问非static成员的所以因此类自定义的实例变量也必须是静态的。 这里不妨回顾一下静态成员变量是属于整个类的仅在类的初次加载时初始化在类被销毁时才会被回收。通过该类实例化的所有对象都共享该静态变量任一对象对于该静态变量的修改都会影响所有的对象。静态方法同样是属于整个类的可以通过类名与对象名进行访问而非静态成员是随着对象的创建而被实例化的。在调用静态方法时可能对象还没有实例化自然也就没有对象的非静态成员的实例化所以无法访问非静态的成员。 2 饿汉式单例模式的实现 在Java中实现单例模式通常有两种形式.: 饿汉式类加载时就进行对象实例化。懒汉式第一次引用类时才进行对象实例化。这里主要聚焦于饿汉式。饿汉式代码实现如下 public class HungrySingLeton {// 创建HungrySingLeton 的一个对象private static final HungrySingLeton instance new HungrySingLeton();// 让构造函数为private这样该类就不会被实例化private HungrySingLeton() {}// 获取唯一可用的对象public static HungrySingLeton getInstance(){return instance;}/*** 获取对象的内存地址* return*/public long getRamAddress() {return VM.current().addressOf(this);} } 注意instance变量加了final的一般建议加final除非说有释放资源等特殊要求。这种方式简单也比较常用在类创建的同时已经创建好一个静态的对象供系统使用执行效率高。 3 饿汉式线程安全 饿汉式单例通过getInstance获取的单例在类加载时已经初始化完毕在多线程环境下也是安全的所以不需要同步。我们可以通过测试来验证。 先写一个公共方法用于多线程环境下获取单例 /*** 公共方法在多线程环境下获取单例避免重复编写测试代码* param threadCount 线程数* param func 函数用于获取单例* param T*/public static T ListT getSingLetonObjList(int threadCount, SupplierT func) {ListT list new ArrayList();ExecutorService executorService Executors.newFixedThreadPool(threadCount);IntStream.range(0, threadCount).forEach(i - {executorService.submit(() - {// 同步锁保证保证内存的可见性否则在多线程环境下可能出现空对象synchronized (SingletonTest.class) {list.add(func.get());}});});executorService.shutdown();while(true) {// 所有的子线程都结束了if(executorService.isTerminated()) {if(list.size() threadCount) {return list;}}}} 这个公共方法可以接收一个函数该函数就是获取单例的方法。值得注意的是那个同步锁如果不加的话在多线程环境下可能会获得空的单例导致后续调用getRamAddress方法时出现空指针。当然也可以用Sytem.out.print方法代替 synchronized (SingletonTest.class) {list.add(func.get()); }等价于System.out.print(); list.add(func.get()); 因为print方法本身就自带锁 public void println(String x) {synchronized (this) {print(x);newLine();} }有了公共方法后接着写测试代码 public static void hungrySingLetonTest() {Supplier func () - HungrySingLeton.getInstance();ListHungrySingLeton list getSingLetonObjList(10, func);list.stream().forEach(item - {System.out.println(内存地址: item.getRamAddress());});} 测试结果如下 多线程下获取到的单例始终是同一个对象他们的内存地址都一样。 4 防止反射破坏单例 到这里可能会认为已经很OK了。但是Java还有个反射机制通过反射可以轻易破解单例的安全。 public static void reflectionTest() throws NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {ClassHungrySingLeton clazz HungrySingLeton.class;// 获取HungrySingLeton的默认构造函数ConstructorHungrySingLeton constructor clazz.getDeclaredConstructor();constructor.setAccessible(true);// 调用默认构造函数创建实例HungrySingLeton h1 constructor.newInstance();HungrySingLeton h2 constructor.newInstance();System.out.println(h1.getRamAddress());System.out.println(h2.getRamAddress());} 得到的结果如下 是两个对象实例既然反射是先获得class也是类的实例再通过calss获得构造函数去获取单例那么解决办法就是在饿汉式构造函数中同步类 public class HungrySingLeton {// 创建HungrySingLeton 的一个对象private final static HungrySingLeton instance new HungrySingLeton();// 让构造函数为private这样该类就不会被实例化private HungrySingLeton() {// 防止防止反射破坏单例synchronized (HungrySingLeton.class) {if(instance ! null){throw new RuntimeException(单例构造器禁止反射调用);}}}// 获取唯一可用的对象public static HungrySingLeton getInstance(){return instance;}/*** 获取对象的内存地址* return*/public long getRamAddress() {return VM.current().addressOf(this);} } 测试结果如下 5 总结 饿汉式单例这种方式简单也比较常用在类创建的同时已经创建好一个静态的对象供系统使用执行效率高。但这种方式下因为还未调用对象就已经创建造成资源的浪费容易产生垃圾对象。
http://www.dnsts.com.cn/news/129848.html

相关文章:

  • 域名备案和网站备案的区别南昌seo专业团队
  • 网站运行维护茂名建设网站
  • ps个人网站黄埔做网站的公司
  • 网站建设与管理培训活动总结飞猪旅游的网站建设
  • 公司网站建设优点苏州建设工程公司网站
  • 购物网站logo站长之家官网
  • 做彩票网站代理赚钱吗做网站哪些软件
  • 珠海做网站多少钱修改wordpress文章id
  • 服务好 售后好的网站建设中铁建设门户网入口
  • 域名网站计划怎么写洛阳网站建设的公司哪家好
  • 厦门满山红网站建设百度官方营销推广平台有哪些
  • 多企业宣传网站建设湖南专业网站建设服务
  • 深圳知名网站建设淮安网站建设公司电话
  • 宇讯网站建设上海有限公司有哪些
  • 北京市海淀区网站建设企业网络推广计划
  • 企业网络营销网站设计wordpress 本地环境
  • 温州网站排名优化公司哪家好装修公司免费网站模版
  • 百度网站建设制作公司家装公司需要什么条件
  • 怎么建设一个宣传网站网站做seo收录
  • jsp网站建设作业东莞专业网
  • 手机端网站模板网站正在建设中模板
  • 接私活 做网站南沙开发区建设和交通局网站
  • 网站建设需要什么样的内容常见的网页布局有哪些
  • 网站后台统计代码网站网页设计内容
  • 永久域名免费注册网站重庆市建设工程信息网官网专家评审
  • 怎么做建设网站首页南昌网站建设大全
  • 中国建设网站工程承包分包法酒店如何做好线上营销
  • 外贸公司没网站旅游网页设计说明书
  • 网软志成免费部队网站源码下载网站建设服务费合同模板
  • 阿里云上如何用iis做网站德州市平原县建设局网站