我有一个类似于以下类的Java类:
public final class Node {
public Node() {}
}
我已经学会了如何通过反射API更改“最终”字段的可访问性,但这对于类也是可行的吗? 我可以在运行时将最终类转换为非final类吗?
答案 0 :(得分:4)
您可以使用ASM等库重写类文件。
在运行时可能没有必要更改类的final
状态,因为在编译子类时它需要非final才能编译子类。
答案 1 :(得分:1)
我不知道这是如何工作的,因为编译器会检查你是否正在尝试在编译时进行非final的类。如果您尝试从中继承,则会收到错误。
我觉得问你这个问题是否好奇,但问自己更大的问题是你为什么要这样做?反射允许你做很多事情来绕过最终,私人等,但这并不意味着它是个好主意。如果第三方图书馆的设计师认为决赛是个好主意,那么你可能会建议你尊重这一点。
答案 2 :(得分:0)
编辑:感谢@kriegaex的评论。 “ accessFlags”字段仅存在于Android SDK中的Class类实现中。因此,除非您是为Android开发的,否则此解决方案将对您不起作用,因为该字段最初并不存在。
在这里,您可以通过删除“最终”修饰符来使类可扩展:
Class classClass = Class.class;
Field accessFlagsField = classClass.getDeclaredField("accessFlags");
accessFlagsField.setAccessible(true);
Class nodeClass = Node.class;
accessFlagsField.setInt(nodeClass, nodeClass.getModifiers() & ~Modifier.FINAL);
我不同意以上答案。可能需要删除“ final”修饰符,以使用“ ASM”或“ byte-buddy”之类的库在运行时扩展类。我同意,如果这是最后一堂课,那可能是有充分理由的,但是自定义业务逻辑可能需要这样做。