[英]Java how to extend a 3rd party application while keeping compatibility
我正在开发基于开放源代码项目的应用程序。 我们向开发人员付款,根据他们的代码制作自己的应用程序(封闭源代码)。 我们确实希望与原始软件包保持兼容,安全性和功能更新将与我们的应用程序合并。
当然,如果我大量修改了原始代码,那么这里最大的问题就是合并新的更新。 我在网上搜索了最佳的解决方案和他人之间,我发现喜欢的网站这一个 。 因此,我决定不尽我所能修改原始代码。 如果要向现有功能添加功能,则可以扩展原始类,使应用程序指向扩展类(这是一个很小的修改,不会造成问题),然后实施我的更改。
这里的问题是我也想扩展的第三方类中的属性。 在下面的示例中, class A
对我希望其继续执行的属性myClass
进行了一些修改。 但是扩展class A
class B
包含一个属性,该属性具有扩展MyClass
本身的类型,此处为MyCustomClass
。 里面class B
我想要的属性myCustomClass
是一个扩展myClass
,对所做的任何更改myClass
应该是在访问myCustomClass
。
据我所知,将myClass
强制转换为myCustomClass
是不可能的,因为myClass
根本不是myCustomClass
类型。 那么,这里最好的解决方案是保持与class A
兼容性,并且不涉及仅复制class A
所有代码,因为如果class A
得到更新,这将产生完全相同的问题?
这里有一些示例代码应该可以更好地解释我的问题:
// Classes 'A' and 'MyClass' are 3rd party, I do not want to edit them
public class A {
private MyClass myClass;
A(){
myClass = new MyClass();
// Changes I want to keep doing
doSomething();
}
public void doSomething(){
// Do some calculations to myClass and modify it accordingly
}
public MyClass getMyClass(){
return myClass
}
}
// Classes 'B' and 'MyCustomClass' are 1st party, I can do anything I want with them :)
public class B extends A{
private MyCustomClass myCustomClass;
B(){
super();
myCustomClass = ?????????;
// Extremely important message, this should keep working
System.out.println(myCustomClass.verySpecialString);
// Build further on made modifications, this should keep working too
useModificationsByClassA();
}
public void useModificationsByClassA(){
// Use result of class A's calculations in order to continue
}
}
public class MyCustomClass extends MyClass{
private String verySpecialString;
MyCustomClass(){
super();
verySpecialString = "Hey!";
}
}
通常,在应用程序,库等中,某些组件被设计为可扩展(尽管如此),而其他某些组件实际上并未被设计为可扩展。
但是,修改现有组件通常不是扩展应用程序行为的方法。
因为现有组件通常不设计为可修改的。 它们的实际逻辑/处理可能会从一个版本到另一个版本发生很大变化。 这些可能会从源代码或其他任何代码中删除。...因此,您将很难将原始源代码的更新合并到应用程序的已修改实现的源代码中。
长话短说:应用程序可以允许扩展,但是在这种情况下,它还提供了扩展点,您不能以任何方式更改任何类。
如果要扩展原始源代码的某些部分,则必须知道实际的应用程序是否旨在扩展,如果需要,如何扩展 。
如果不是为了扩展而设计的,则您应该接受应用程序更新可能未集成(或难以集成)到修改后的应用程序中。
考虑使用适配器或装饰器模式,并使用合成代替继承。 例如:
public class B {
private final A a;
private final MyCustomClass myCustomClass;
B(A a) {
this.a = a;
myCustomerClass = new MyCustomClass(a.getMyClass());
}
public void doSomething() {
a.doSomething(); // updates the state of a.myClass.
myCustomerClass.doSomething(); // use the change of a.myClass to do more stuff
}
}
public class MyCustomClass {
private final MyClass myClass;
private String verySpecialString;
public MyCustomClass(MyClass myClass) {
this.myClass = myClass;
}
public void doSomething() {
verySpecialString = "Hey!" + myClass.getSomeResult();
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.