簡體   English   中英

Java如何在保持兼容性的同時擴展第三方應用程序

[英]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.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM