Java - 在超类中注入资源而不暴露基类中的Setter

时间:2015-12-20 16:26:27

标签: java

也许这是一个简单的问题,但我仍然没有为它提供解决方案。我有这种类的配置:

abstract class SuperA {
   Resource a;
   Resource b;

   public SuperA() {
   }

   public SuperA(Resource a, Resource b) {
      this.a = a;
      this.b = b;
   }

   protected Resource getResourceA() {
       return a;
   }

   protected Resource getResourceB() {
       return b;
   }

}

class BaseA extends SuperA {
   public method1() {
       Resource myResource = getResourceA();
   }
}

class Manager {
   public Manager() {
      // I want to instantiate BaseA and inject some resources, but can't do
      // it through the constructor
      BaseA baseA = new BaseA(/*can't place parameters*/);
      // I could use Setters, but this would expose the Setters to BaseA too...
      baseA.setResourceA(new Resource());
      baseA.setResourceB(new Resource());
   }
}

在这种情况下,我想将资源注入Super类而不将任何Setter暴露给它的Base类而不继承构造函数,有没有办法做到这一点?

更新 - 澄清

BaseA类是API的扩展,我不希望其他用户有权修改实例化BaseA的核心引擎注入的资源。我希望BaseA 使用资源 NOT 来修改它们。

1 个答案:

答案 0 :(得分:1)

一个选项就是像这样的设定者,它是“包装可见的'并且' final'

  

您在方法声明中使用final关键字来表示   方法不能被子类覆盖。来自javadoc

然后你用'包私人'访问级别修饰符(不是精确的引用,但要解释)

  

(没有'公共','私人',或'受保护'陈述)这意味着   类本身可以在同一个包中看到/使用方法,类   可以看到/使用该方法,但子类和世界不能看到/使用   方法From javadoc

'包私人'单独可能会解决你的问题,但我会把#final;#39;只是为了使所需的行为更加明显,以便有助于未来的代码工作等。

例如:

abstract class SuperA {
   // making these private also helps
   // because it limits child classes to ONLY use getters
   // they can't even 'fiddle with' the raw values
   private Resource a;
   private Resource b;

   // would you want this public? perhaps also no 'access-modifier' 
   // the 'exact' specifics of a lot of this class would depend on your
   // specific use case (But I'd think you would want this package-only too most likely)
   public SuperA() {
   }

   // note no 'access-modifier', means package use only.
   SuperA(Resource a, Resource b) {
      this.a = a;
      this.b = b;
   }


   // can also have the same with setters
   // again no 'access-modifier' 
   final setResourceA(Resource a){ this.a = a;}
   final setResourceB(Resource b){ this.b = b;}

   public final Resource getResourceA() {
       return a;
   }


   public final Resource getResourceB() {
       return b;
   }

}

这将允许您的图书馆访问这些方法,但不允许子类或世界'