将Getters / Setter添加到一个Base类

时间:2013-05-10 12:50:37

标签: java generics

我有一个想法,但无法弄清楚如何实现这一点。

public class BaseDomain<T>{

//Generic methods goes here

}

public class Domain1 extends BaseDomain<Domain1>{

private int id;

private String name;

//only properties should be present here

}

public class Domain2 extends BaseDomain<Domain2>{

private int id;

private String name;

//only properties should be present here

}

在上面的场景中,我可以轻松地在基类中定义所有泛型方法,并且可以使用泛型在我的所有域类中使用。但我的问题是我想设计一个机制,开发人员必须只在域类中定义属性(没有getter / setter)但是BaseDomain应该提供 getters / setters动态到每个域。

任何建议都非常感谢!

5 个答案:

答案 0 :(得分:2)

使用Java的常规功能无法做到这一点。

您可以使用Lombok等工具。

我个人不喜欢这种方法,因为它会在你的项目中引入“魔力”,这在某些时候会引起麻烦,只会节省一些样板代码。

答案 1 :(得分:2)

使用 Reflection ,你可以做到这一点。

public class BaseDomain<T>{


    public String getName() {
        return this.getClass().getField("name").get(this);
    }

    public void setName(String value) {
        this.getClass().getField("name").set(this, value);
    }

}

请注意,this.getClass()将引用该对象的运行时类,例如Domain1。因此,您可以访问那里的字段,获取/设置值等

如果您将属性声明为privateprotected,则可能需要设置访问权限。它们是public,它应该有效。

正如OP所提到的,使用getDeclaredFields()不会强制您声明公共字段,遗憾的是您必须通过迭代(或使用Map)来访问具有特定名称的Field

如果对象实例中不存在该字段,则会出现异常。

答案 2 :(得分:0)

这听起来像你应该使用一个接口。使用接口可以定义必须提供的功能,并且实现它的类必须提供它们。在你的代码中,你永远不会只引用特定的类接口,就像一个类。

示例:

public interface MyInterface
{
     public String getName();
}

public MyClass implements MyInterface
{
    public String getName { return " test"; }
}

public OtherClass
{
    private MyInterface = new MyClass();
}

如果您不希望程序员实现您的接口,那么这只能通过反射来完成。您可以使用代理对象来实现getter和setter,并通过此对象访问它们,如下所述:{{ 3}}

答案 3 :(得分:0)

如果你的代码没有某种预处理器,你就无法做到。预处理器将在编译之前解析Java文件,添加所需的方法,然后将生成的预处理文件推送到编译器。无论如何,看到Java是一种静态类型的语言 - 这是一个非常糟糕的主意。

如果您希望它是动态的,您可以使用 Groovy 而不是Java。 Groovy是一种单独的语言,它与Java共享很多并编译为JVM字节码。但是,它允许您非常轻松地制作这种“动态”方法。

答案 4 :(得分:0)

基类中定义的任何变量,getter和setter都可以在扩展基类的类中使用,假设访问级别修饰符允许使用。

以下是一个例子:

public class BaseClass {

    private int id;

    private String name;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

}

class AnotherClass extends BaseClass {

    public String getIdString() {
        return Integer.toString(getId());
    }
}

由于id在基类中被定义为private,因此扩展类可以获取id的唯一方法是使用public getId方法。通过使用getId和setId方法。扩展类可以使用Id字段而无需定义它。

如果您希望扩展类可以访问字段本身,则必须保护字段,而不是私有字段。

扩展类只需要定义它们自己需要的getter和setter。他们可以使用已在基类中定义的getter和setter,同样假设访问级别修饰符允许使用。