【问题标题】:Java: Adding fields and methods to existing Class?Java:向现有类添加字段和方法?
【发布时间】:2012-12-05 19:28:46
【问题描述】:

在 Java 中是否有一种方法可以将一些字段和方法添加到现有类? 我想要的是我有一个类导入到我的代码中,我需要添加一些从现有字段派生的字段及其返回方法。 有没有办法做到这一点?

【问题讨论】:

  • 你能继承现有的类吗?
  • 您可以扩展您拥有的类并在新类中添加新方法...
  • 你控制源吗?考虑扩展或组合。
  • 我不知道为什么人们不赞成这个......我认为这家伙想要的是相当于 C# 的扩展方法,你不必继承类 A,但你可以编写一个扩展方法 foo(),然后你可以调用任何 A 或继承自 A... (A.foo()) 的东西。现在我不知道是否有这样的东西,但它非常有用。
  • 我也在寻找 Daniel 上面描述的功能。我不能对现有类(Selenium 的 Window 类)进行子类化,因为很多框架代码都会实例化它,而我不能更新它们来实例化我的子类。所以我需要在这个类中注入一些方法。另一种方法是创建一个新的类层次结构,但将方法直接注入 Window 类会更干净。 Java 有没有类似于 C# 的扩展方法?

标签: java methods field add


【解决方案1】:

您可以创建一个类来扩展您希望添加功能的类:

public class sub extends Original{
 ...
}

要访问超类中的任何私有变量,如果没有 getter 方法,您可以将它们从“私有”更改为“受保护”并能够正常引用它们。

希望有帮助!

【讨论】:

  • OP 询问是否要添加到 existing 类,因此建议创建一个新类显然不能满足请求。
【解决方案2】:

您可以在 Java 中扩展类。例如:

public class A {

  private String name;

  public A(String name){
    this.name = name;
  }

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

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

}

public class B extends A {
  private String title;

  public B(String name, String title){
    super(name); //calls the constructor in the parent class to initialize the name
    this.title= title;
  }      

  public String getTitle(){
    return this.title;
  }

  public void setTitle(String title) {
    this.title= title;
  }
}

现在B 的实例可以访问A 中的公共字段:

B b = new B("Test");
String name = b.getName();
String title = b.getTitle();

更多详细教程请查看Inheritance (The Java Tutorials > Learning the Java Language > Interfaces and Inheritance)

编辑:如果类 A 有一个构造函数,例如:

public A (String name, String name2){
  this.name = name;
  this.name2 = name2;
}

那么在B课堂上你有:

public B(String name, String name2, String title){
  super(name, name2); //calls the constructor in the A 
  this.title= title;
}

【讨论】:

  • 谢谢,很有帮助!现在我可以使用多少个超级(字段),因为如果 ex 的构造函数。上层范式有两个领域,第二个是错误的。
  • 啊,你只需给 super 打一个电话。基本上它是调用父类的构造函数。所以你只在构造函数中调用它一次,它必须是第一行。见编辑。
【解决方案3】:

这些示例仅在您扩展的类不是最终类时才真正适用。例如,您不能使用此方法扩展 java.lang.String。但是还有其他方法,例如使用 CGLIB、ASM 或 AOP 进行字节码注入。

【讨论】:

    【解决方案4】:

    假设这个问题是关于 C# 扩展方法或 JavaScript 原型的等价物,那么从技术上讲,Groovy 做了很多事情是可能的。 Groovy 编译 Java 并且可以扩展任何 Java 类,甚至是最终类。 Groovy 有 metaClass 来添加属性和方法(原型)例如:

    // Define new extension method
    String.metaClass.goForIt = { return "hello ${delegate}" }
    
    // Call it on a String
    "Paul".goForIt() // returns "hello Paul"
    
    // Create new property
    String.metaClass.num = 123
    
    // Use it - clever even on constants
    "Paul".num // returns 123
    "Paul".num = 999 // sets to 999
    "fred".num // returns 123
    

    我可以解释如何像 Groovy 那样做,但对于发帖者来说,这可能太多了。如果他们愿意,我可以研究和解释。

    【讨论】:

    • 这篇文章没有要求解释 Groovy 特性。
    • 正确 - 我试图帮助添加更多信息。显然,扩展/子类化是通常的方式,很多人都指出了这一点,但是如果出于某种原因我们从字面上理解提问者 --- 他想将字段/方法添加到 Java 中的现有类中,那么这不适合轻松的心。 Groovy 基本上是一种改进的鸭式 Java。他们添加的功能之一就是这种能力。 Groovy 非常棒,作为一名 Java 程序员,我建议自己研究一下。
    • 是的,我理解,而且我什至可能同意你对 Groovy 的看法,但是当有人来这里寻求 Java 帮助时,Groovy 广告并不是正确的答案。
    • 这个答案与 java.lang.reflections 没有任何关系。我什至不明白这是什么。
    • 实际上我的回答确实与 Java 有很大关系 :-) Groovy 可以扩展 Java 类,然后您可以从 Java 代码中使用它。 Groovy 是一种 JVM 语言。希望这能解释我的理由。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-06-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-01-11
    相关资源
    最近更新 更多