模板模式使用匿名内部类扩展

模板模式的定义:
       它定义了一个操作中的算法骨架,将某些步骤延迟到子类中实现,这样子类才可以不改变算法结构的前提下重新定义改算法的某些特定步骤。

模板模式的核心:
       处理的步骤父类中早已定义好,具体的实现延迟到子类中去完成。

模板方法的角色:
       1.抽象模板角色:它一般是一个抽象类或者接口,它抽象出操作算法骨架。
       2.具体抽象模板角色:它实现了抽象模板角色的方法,它是操作算法骨架业务的具体化。

模板方法的优点:
        1.封装不变部分,扩展可变部分。
         2.提取了公共代码,便于维护。
          3.行为由父类控制,子类实现。

模板方法的缺点:
         1.每一个不同的实现都需要一个子类来实现,这样导致类的个数增加。

模板模式的使用场景:      
          1.实现一个算法时,基本步骤很固定,但是某些部分易变,易变的部分可以抽离出来,由子类实现。

 

匿名内部类:

          没有名字,定义在其他类方法中的类

 * 作用:把定义子类,重写父类的方法,创建子类对象,合成一步完成

 * 把定义实现类,重写接口的抽象方法,创建实现类对象,合成一步完成

 * 结果:就是一个子类对象,子类对象没有名字

 

针对模板方法的缺点,我们使用匿名内部类,扩展模板模式。

如下,两个主要方法,save/find, 保存学生失败(这里暂定姓名为主键,主键冲突),那么进行查询。

 

测试类:

public class TestInnerClass {

    private StudentDao studentDao;

    public static void main(String[] args) {

        TestInnerClass t = new TestInnerClass();

        Student student1 = new Student("1", "张三");

        Student s1 = t.saveAndGetStudent(student1);

        System.out.println(s1);

        Student student2 = new Student("2", "李四");

        Student s2 = t.saveAndGetStudent(student2);

        System.out.println(s2);
    }

    public Student saveAndGetStudent(Student s) {

        studentDao = new StudentDaoImpl();

        //模板模式
        return RepositoryUtils.saveOrFind(new RepositoryUtils.function<Student>() {

            @Override
            public Student save() {
                return studentDao.saveStudent(s);
            }

            @Override
            public Student find() {
                return studentDao.findStudent(s);
            }
        });
    }
}

 

0.

public class Student {

    private String sId;
    private String sName;

    public Student() {
    }

    public Student(String sId, String sName) {
        this.sId = sId;
        this.sName = sName;
    }

    public String getsId() {
        return sId;
    }

    public void setsId(String sId) {
        this.sId = sId;
    }

    public String getsName() {
        return sName;
    }

    public void setsName(String sName) {
        this.sName = sName;
    }

    @Override
    public String toString() {
        return "Student{" +
                "sId='" + sId + '\'' +
                ", sName='" + sName + '\'' +
                '}';
    }
}

1.

public interface StudentDao {

    Student findStudent(Student s);

    Student saveStudent(Student s);

}

2.

public class StudentDaoImpl implements StudentDao {

    @Override
    public Student findStudent(Student s) {

        //查库逻辑.. 略

        return new Student(
                "1",
                "张三"
        );
    }

    @Override
    public Student saveStudent(Student s) {

        //存库逻辑.. 略

        if ("张三".equals(s.getsName())) {
            throw new DataIntegrityViolationException("主键冲突.");
        }

        return new Student(
                "2",
                "李四"
        );
    }
}

3.

public class RepositoryUtils {


    interface function<T> {

        T save();

        T find();
    }


    public static <T> T saveOrFind(function<T> function) {
        try {
            return function.save();
        } catch (DataIntegrityViolationException e) {
            return function.find();
        }
    }


}

 

interface function<T> {

        T save();

        T find();
    }
 

对接口function的操作,即,把定义实现类,重写接口的抽象方法,创建实现类对象,合成一步完成。

 

end!

 

ref:

https://blog.csdn.net/sunshine_0707/article/details/86610368

https://www.cnblogs.com/east7/p/9564917.html

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值