单例模式:
为什么使用单例: 节省内存资源, 保证数据的一致性。此外很多时候整个系统只需要拥有一个全局对象,有利于我们协调系统整体的行为。
代码模拟:
/*** 饿汉式: 在加载类时候创建类的实例,并保存在类中* 线程安全 但浪费资源*/public class HungrySingleton {private HungrySingleton() {}private static final HungrySingleton instance = new HungrySingleton();public static HungrySingleton getInstance() {return instance;}}===============/*** 懒汉式: 不在系统加载时创建类的单例, 而是第一次使用实例时候创建。*/public class LazySingleton {/*** 保证 instance 在所有线程中同步*/private static LazySingleton instance = null;/*** 避免在外部被实例化*/private LazySingleton(){}public static synchronized LazySingleton getInstance() {if(instance == null) {instance = new LazySingleton();}return instance;}}================/*** 双重加锁机制*/public class DoubleLockLazySingleton {/*** volatile关键字的含义是:被其所修饰的变量的值不会被本地线程缓存,所有对该变量的读写都是直接操作共享内存来实现,从而确保多个线程能正确的处理该变量。* 该关键字可能会屏蔽掉虚拟机中的一些代码优化,所以其运行效率可能不是很高,所以,一般情况下,并不建议使用双重加锁机制,酌情使用才是正理!** 更进一步说,其实使用volatile的目的是为了防止暴露一个未初始化的不完整单例实例,导致系统崩溃。* 因为创建单例实例其实需要经过以下几步:* 首先分配内存空间、然后将内存空间的首地址指向引用(指针),最后调用构造器创建实例,由于在第二步的时候这个引用(指针)就会变的非null,* 那么在第三步未执行,真正的单例实例还未创建完成的时候,一个线程过来在第一个校验中为false,将会直接将不完整的实例返回,从而造成系统崩溃。*/private static volatile DoubleLockLazySingleton instance = null;private DoubleLockLazySingleton() {}public static DoubleLockLazySingleton getInstance() {if(instance == null) {//区域1//不同线程去抢夺锁资源synchronized (DoubleLockLazySingleton.class) {//区域2if(instance == null) {//区域3/*** 这里还要进行判断的原因是: 如果两个线程都进入到区域1* A线程抢到了锁, 实例话对象,如果不加判断, B线程进入同步块也会初始化对象 违反单例原则。*/instance = new DoubleLockLazySingleton();}}}//单例存在, 不需要同步操作. 直接返回该引用return instance;}}==================/*** 静态内部类* 内部类和其外部类之间没有从属关系, 加载外部类时候不会加载静态内部类, 只有在调用时候才会加载, 创建单例对象返回,实现懒加载。* 同步问题: 使用静态初始化器的方式,借助jvm实现线程安全*/public class ClassInnerClassSingleton {public static class Singleton {private static ClassInnerClassSingleton instance = new ClassInnerClassSingleton();}private ClassInnerClassSingleton() {}public static ClassInnerClassSingleton getInstance() {return Singleton.instance;}}public class ClassInnerClassSingleton2{private static ClassInnerClassSingleton2 instance = null;static {instance = new ClassInnerClassSingleton2();}private ClassInnerClassSingleton2() {}public static ClassInnerClassSingleton2 getInstance() {return ClassInnerClassSingleton2.instance;}public static void main(String[] args) {new Thread(() -> System.out.println(ClassInnerClassSingleton2.getInstance().hashCode())).start();new Thread(() -> System.out.println(ClassInnerClassSingleton2.getInstance().hashCode())).start();new Thread(() -> System.out.println(ClassInnerClassSingleton2.getInstance().hashCode())).start();}}
工厂模式:
代码模拟:
=== 简单工厂模式 ===
public interface INoodles {
/**
* 描述每种面条啥样的
*/
public abstract void desc();
}
public class LzNoodles implements INoodles {
@Override
public void desc() {
System.out.println("兰州拉面,兰州特色小吃");
}
}
public class PaoNoodles implements INoodles {
@Override
public void desc() {
System.out.println("泡面,程序员必备");
}
}
public class ReganNoodles implements INoodles {
@Override
public void desc() {
System.out.println("红油热干面,武汉特色小吃");
}
}
/**
* 简单工厂模式
* 一家“简单面馆”(简单工厂类)
*/
public class SimpleNoodlesFactory {
public static final int TYPE_LZ = 1;//兰州拉面
public static final int TYPE_PM = 2;//泡面
public static final int TYPE_GK = 3;//热干面
/**
* 如果生产对象的方法是static的,这种简单工厂也叫做静态工厂
* 如果生产对象的方法不是static的,这种简单工厂也叫做实例工厂
* @param type
* @return
*/
public static INoodles createNoodles(int type) {
switch (type) {
case 1:
return new LzNoodles();
case 2:
return new PaoNoodles();
case 3:
return new ReganNoodles();
default:
return new LzNoodles();
}
}
}
public class test {
public static void main(String[] args) {
/*自己不必关心面条怎么做(怎么new,如何new)让面馆操心去吧(面馆帮我们new)!*/
INoodles iNoodles = SimpleNoodlesFactory.createNoodles(2); // 和具体的对象脱离关系
iNoodles.desc();
}
}
---------------------
/**
* 工厂方法模式
*/
public interface INoodlesFactory {
INoodles createNoodles();
}
public class LzINoodlesFactory implements INoodlesFactory {
@Override
public INoodles createNoodles() {
return new LzNoodles();
}
}
public class PaoINoodlesFactory implements INoodlesFactory {
@Override
public INoodles createNoodles() {
return new PaoNoodles();
}
}
public class ReganINoodlesFactory implements INoodlesFactory {
@Override
public INoodles createNoodles() {
return new ReganNoodles();
}
}
public class Test {
public static void main(String[] args) {
INoodlesFactory noodlesFactory = new LzINoodlesFactory();
INoodles noodles = noodlesFactory.createNoodles();
noodles.desc();
}
}
代理模式:
代码模拟:
静态代理:
/**
* 接口:租房
*/
public interface IRentingHouse {
void rentHosue();
}
public class RentingHouseImpl implements IRentingHouse {
@Override
public void rentHosue() {
System.out.println("我要租用一室一厅的房子");
}
}
public class RentingHouseProxy implements IRentingHouse {
private IRentingHouse rentingHouse;
public RentingHouseProxy(IRentingHouse rentingHouse) {
this.rentingHouse = rentingHouse;
}
@Override
public void rentHosue() {
System.out.println("中介(代理)收取服务费3000元");
rentingHouse.rentHosue();
System.out.println("客户信息卖了3毛钱");
}
}
public static void main(String[] args) {
IRentingHouse rentingHouse = new RentingHouseImpl();
RentingHouseProxy rentingHouseProxy = new RentingHouseProxy(rentingHouse);
rentingHouseProxy.rentHosue();
}
-----------------------------------
动态代理:
jdk代理: 系统自带的代理
/**
* Jdk动态代理
*
* @param obj 委托对象
* @return 代理对象
*/
public Object getJdkProxy(Object obj) {
// 获取代理对象
return Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(),
new InvocationHandler() {
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object result = null;
// 写增强逻辑
System.out.println("中介(代理)收取服务费3000元");
// 调用原有业务逻辑
result = method.invoke(obj, args);
System.out.println("客户信息卖了3毛钱");
return result;
}
});
}
public static void main(String[] args) {
IRentingHouse rentingHouse = new RentingHouseImpl(); // 委托对象---委托方
// 从代理对象工厂获取代理对象
IRentingHouse jdkProxy = (IRentingHouse) ProxyFactory.getInstance().getJdkProxy(rentingHouse);
jdkProxy.rentHosue();
}
--------------------------------------
cglib代理:
/**
* 使用cglib动态代理生成代理对象
*
* @param obj 委托对象
* @return
*/
public Object getCglibProxy(Object obj) {
return Enhancer.create(obj.getClass(), new MethodInterceptor() {
@Override
public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
Object result = null;
System.out.println("中介(代理)收取服务费3000元");
result = method.invoke(obj, objects);
System.out.println("客户信息卖了3毛钱");
return result;
}
});
}
public static void main(String[] args) {
RentingHouseImpl rentingHouse = new RentingHouseImpl(); // 委托对象
// 使用工厂来获取代理对象
RentingHouseImpl cglibProxy = (RentingHouseImpl) ProxyFactory.getInstance().getCglibProxy(rentingHouse);
cglibProxy.rentHosue();
}

