博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
悠然乱弹:从几个方法的重构讲开去--注解相关的处理
阅读量:5749 次
发布时间:2019-06-18

本文共 4824 字,大约阅读时间需要 16 分钟。

有时候它们的处理没有关联性,有些时候,它们的处理又是有关联性的。

我们用伪代码来示意一下。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
if
(includeAnnotation(testClass,Abc.
class
)){
  
doSomething...
}
 
if
(includeAnnotation(testClass,Abc.
class
)){
  
for
(Field field:testClass.getFields){
    
if
(includeAnnotation(testField,AbcField.
class
)){
     
dosomething...
   
}
  
}
  
for
(Method method:testClass.getMethods){
    
if
(includeAnnotation(testMethod,AbcMethod.
class
)){
     
dosomething...
   
}
  
}
}
你会发现所有的注解过程处理都是上面几种情况。

有的时候,我们可能在类名的处理上还有一些规则,比如:....Service,.....Action,.....View等等,我们的某些注解只可以加在某种类名规则之下,这个时候,判定就又会增加。我们的程序员就不停的在写这些重复,但是却不可缺少的内容。有没有办法让开发人员只写doSomething的内容就好呢??

只要问题可以提得出来,办法总是有的:

可以定义下面的三个类,开发人员只要编写process函数体中的内容就好了。

1
2
3
4
5
6
7
8
9
public
interface
AnnotationClassAction {
    
<T>
void
process(Class<T> clazz, Annotation annotation);
}
public
interface
AnnotationMethodAction {
    
<T>
void
process(Class<T> clazz, Method method, Annotation annotation);
}
public
interface
AnnotationPropertyAction{
    
<T>
void
process(Class<T> clazz, Field field, Annotation annotation);
}

这对于开发人员来说当然是再熟悉不过的了。

但是总要让上面的逻辑有所体现才是,否则不是就执行错位置了??

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
<
annotation-class-matchers
>
    
<
annotation-class-matcher
class-name
=
".*\.annotation\.Annotation.*"
        
annotation-type
=
".*Test"
>
        
<
processor-beans
>
            
<
processor-bean
enable
=
"true"
name
=
"classAction"
>
            
</
processor-bean
>
        
</
processor-beans
>
        
<
annotation-method-matchers
>
            
<
annotation-method-matcher
method-name
=
"method.*"
                
annotation-type
=
".*Test"
>
                
<
processor-beans
>
                    
<
processor-bean
enable
=
"true"
name
=
"methodAction"
>
                    
</
processor-bean
>
                
</
processor-beans
>
            
</
annotation-method-matcher
>
        
</
annotation-method-matchers
>
        
<
annotation-property-matchers
>
            
<
annotation-property-matcher
                
property-name
=
"field.*"
annotation-type
=
".*Test"
>
                
<
processor-beans
>
                    
<
processor-bean
enable
=
"true"
name
=
"propertyAction"
>
                    
</
processor-bean
>
                
</
processor-beans
>
            
</
annotation-property-matcher
>
        
</
annotation-property-matchers
>
    
</
annotation-class-matcher
>
</
annotation-class-matchers
>

上面的演示了一个 示例,看起来比较复杂,其实是因为配置的内容为了充分说明,所以看起来有点复杂,实际应用情况不一定要全配的。我给翻译一下:

1
2
3
4
5
首先进行注解类的匹配,匹配的类名是*.annotation.Annotation.*,上面加的注解名是*Test,如果匹配呢,就执行classAction处理器。
 
如果类名匹配,则再进行方法匹配,方法名必须是method*格式的,上面加的注解是*Test类型的注解,匹配成功呢就执行methodAction处理器。
 
如果类名匹配,再进行属性匹配,属性名必须为field*格式,上面的注解格式是*Test类型,如果匹配呢就执行propertyAction处理器。

这样是不是简单了,把所有的匹配工作都通过配置的方式进行实现,开发人员只需要做逻辑处理的部分。

比如下面这样子:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public
class
AnnotationClassActionDemo
implements
AnnotationClassAction {
    
public
<T>
void
process(Class<T> clazz, Annotation annotation) {
        
System.out.println(
"className:"
+ clazz.getName() +
" annotation类型:"
                
+ annotation.annotationType().getName());
    
}
}
 
public
class
AnnotationMethodActionDemo
implements
AnnotationMethodAction {
    
public
<T>
void
process(Class<T> clazz, Method method,
            
Annotation annotation) {
        
System.out.println(
"className:"
+clazz.getName()+
" annotation类型:"
+annotation.annotationType().getName()+
" method名称:"
+method.getName());     
    
}
}
 
public
class
AnnotationPropertyActionDemo
implements
        
AnnotationPropertyAction {
 
    
public
<T>
void
process(Class<T> clazz, Field field, Annotation annotation) {
        
System.out.println(
"className:"
+ clazz.getName() +
" annotation类型:"
                
+ annotation.annotationType().getName() +
" field名称:"
                
+ field.getName());
    
}
}
针对下面的类:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
@Test
(id=
0
,description=
"class"
)
@XStreamAlias
(
"sd"
)
public
class
AnnotationDemo1 {
    
@Test
(id=
1
,description=
"field1"
)
    
private
String field1;
    
@Test
(id=
2
,description=
"field2"
)
    
private
String field2;
    
@Test
(id=
3
,description=
"method1"
)
    
public
void
method1(){
        
System.out.println(
"method1"
);
    
}
    
@Test
(id=
4
,description=
"method2"
)
    
public
void
method2(){
        
System.out.println(
"method2"
);
    
}
    
public
String getField1() {
        
return
field1;
    
}
    
public
void
setField1(String field1) {
        
this
.field1 = field1;
    
}
    
public
String getField2() {
        
return
field2;
    
}
    
public
void
setField2(String field2) {
        
this
.field2 = field2;
    
}
}

进行处理,可以看到正确的处理结果。

1
2
3
4
5
className:org.tinygroup.annotation.AnnotationDemo1 annotation类型:org.tinygroup.annotation.Test
className:org.tinygroup.annotation.AnnotationDemo1 annotation类型:org.tinygroup.annotation.Test field名称:field1
className:org.tinygroup.annotation.AnnotationDemo1 annotation类型:org.tinygroup.annotation.Test field名称:field2
className:org.tinygroup.annotation.AnnotationDemo1 annotation类型:org.tinygroup.annotation.Test method名称:method1
className:org.tinygroup.annotation.AnnotationDemo1 annotation类型:org.tinygroup.annotation.Test method名称:method2

通过上面的的重构,我们可以看到,把开发人员从重复的劳动中解脱出来,而且由于其只处理逻辑部分的内容即可,也避免了一些不必要的逻辑错误引入。

当然,采用配置还是编码的方式配置匹配规则,这个是公说公有理,婆说婆有理,其实两者都支持不就可以了??

总之,通过上面的重构,对编程人员开发注解方面有更大的便捷。

通过文件处理及注解处理的重构,我们看到代码编写及实现确实是优雅了,

解决了代码重复、圈复杂度大、扩展方面的问题,但是性能方面的问题其实是还没有解决的。

转载地址:http://ayrzx.baihongyu.com/

你可能感兴趣的文章
【探索HTML5第二弹01】HTML5的前世今生以及来世
查看>>
Failed to connect to remote VM. Connection refused. Connection refused: connect
查看>>
freeze
查看>>
SAP HANA存储过程结果视图调用
查看>>
设计模式 ( 十八 ):State状态模式 -- 行为型
查看>>
OracleLinux安装说明
查看>>
nova分析(7)—— nova-scheduler
查看>>
Entity Framework 实体框架的形成之旅--Code First模式中使用 Fluent API 配置(6)
查看>>
OpenMediaVault 搭建git,ssh无法连接问题
查看>>
java多线程之:Java中的ReentrantLock和synchronized两种锁定机制的对比 (转载)
查看>>
【Web动画】SVG 实现复杂线条动画
查看>>
使用Wireshark捕捉USB通信数据
查看>>
Apache Storm 官方文档 —— FAQ
查看>>
iOS 高性能异构滚动视图构建方案 —— LazyScrollView
查看>>
Java 重载、重写、构造函数详解
查看>>
【Best Practice】基于阿里云数加·StreamCompute快速构建网站日志实时分析大屏
查看>>
【云栖大会】探索商业升级之路
查看>>
HybridDB实例新购指南
查看>>
C语言及程序设计提高例程-35 使用指针操作二维数组
查看>>
华大基因BGI Online的云计算实践
查看>>