Java注释重载?

时间:2010-09-03 02:16:06

标签: java annotations overloading

在我的项目中,我已经定义了类似于以下内容的注释:
(为简洁省略@Retention@Target

public @interface DecaysTo {
    String[] value();
}

自从最初编写它以来,我们的需求已经改变,我现在已经定义了一个我希望能够用来代替字符串的枚举:

public enum Particle {
    ELECTRON,
    ANTIELECTRON,
    NEUTRINO,
    ANTINEUTRINO,
    ...
}

为避免更新此批注的每个实例,我希望能够使用 String {{{{{{ 1}} 没有必须更新此批注的每个实例以指定属性。但是,由于我们定义了注释的属性,而不是构造函数,因此似乎无法重载它。

enum Particle

还尝试了:

// In a perfect world, either of these would work ...
public @interface DecaysTo {
    String[] value();
    Particle[] value();
}

@DecaysTo({"Electron", ...})
@DecaysTo({Particle.ELECTRON, ...})

// without having to explicitly specify which attribute to set:
public @interface DecaysTo {
    String[] stringVals();
    Particle[] enumVals();
}

@DecaysTo(stringVals = {"Electron", ...})
@DecaysTo(enumVals = {Particle.ELECTRON, ...})

是否有任何方式来执行此操作,不涉及返回并编辑大量代码?

3 个答案:

答案 0 :(得分:4)

最好的方法是查找并替换以前的所有注释。你不希望旧的设计挥之不去。在整个重构过程中保持干净的代码库。

假设您不想这样做,或者您不拥有使用注释的代码,则应保留两种注释类型。在您的注释处理代码中,您查找两者,如果使用旧的,则将其转换为新的。

DecaysToV2 anno = getAnnotation( DecaysToV2.class );
if(anno = null)
{
    DecaysTo anno_old = getAnnotation( DecaysTo.class );
    if(anno_old!=null)
       anno = convert (anno_old);
}

DecaysToV2只是一个你可以提出的界面:

DecaysToV2 convert( DecaysTo old )
{
    DecaysToV2Impl impl = new DecaysToV2Impl();
    impl.value = ...
    return impl;
}
static class DecaysToV2Impl implements DecaysToV2
{
    Particle[] value;
    public Particle[] value(){ return this.value; }
} 

答案 1 :(得分:2)

您可以弃用此注释,并为新代码引入一个新注释(例如@DecaysToParticle)。

答案 2 :(得分:1)

也许你真正需要的是

enum Particle {
    ELECTRON("Electron"),
    ...

    private String name;
    private Particle(String name) {
        this.name = name;
    }
    public String getName() {return name;}
}

(您也可以使用字符串函数生成名称,但此apporach更灵活。)

此外,我不明白必须更改大量的代码,因为(我猜)你的建议无法编译,我希望这不是你的代码实际上是什么样的。