2016-08-21 97 views
0

我有一個「標準」JPanel內有兩個面板。我試圖創建一種模板類,然後擴展它並實現內容。問題是關於實施它的方式。如何用靜態工廠方法創建抽象類?

下面的代碼是我試圖使它工作,但我剛開始閱讀有效的Java書,我不熟悉靜態工廠方法。特別試圖抽象它們。

,我試圖專門遵循一些從書上的提示是

  • 考慮靜態工廠方法代替構造
  • 青睞組成了繼承
  • 不想接口抽象類

但我無法找到一個很好的解決方案尊重這些要點(沒有他們:P)。

public abstract class CentralPage { 

    static JPanel getInstance() { 
     JPanel container = new JPanel(); 
     container.setBackground(Color.white); 
     container.setBorder(
       BorderFactory.createCompoundBorder(new LineBorder(Color.BLACK), new EmptyBorder(10, 10, 10, 10))); 
     container.setMinimumSize(new Dimension(960, 400)); 
     container.setPreferredSize(new Dimension(960, 400)); 
     container.setLayout(new BoxLayout(container, BoxLayout.Y_AXIS)); 

     JPanel up = getUp(container); 
     container.add(up); 
     JPanel down = getDown(container); 
     container.add(down); 
     return container; 
    } 

    abstract JPanel getDown(JPanel container); 

    abstract JPanel getUp(JPanel container); 

} 

隨意問您是否需要更多關於其他代碼部分的信息。

+0

你想要解決什麼[*問題*](http://meta.stackoverflow.com/q/66377/163188) – trashgod

+0

我想,我有一個抽象類與默認的靜態工廠方法,但它是不可能的在抽象類上添加靜態方法。所以我試圖找到標準的工作。更好? –

+0

提供靜態工廠方法而不是構造函數的基本思想是隱藏實現。這些實現隱藏在私有或匿名類中。你的方法看起來更像抽象工廠方法。你應該提供一個通用的工廠界面,然後可以用來定製你的面板。儘管如此,如果需要,仍然可以將工廠方法的「默認」實現作爲靜態方法提供。 – kaetzacoatl

回答

3

Java靜態方法不能抽象 - 更長的討論here

現在讓我們分解你的建築:你的最終結果應該是一個JPanel有兩個孩子,也JPanels,其自己的建設取決於父母JPanel。你希望這種結構可以用靜態工廠方法來完成。

如果這是正確的,這可能是一個解決方案:

public interface UpDown{ 
    public JPanel getUp(JPanel parent); 
    public JPanel getDown(JPanel parent); 
} 

public class CentralPage{ 
    static JPanel getInstance(UpDown components){ 
     JPanel container = new JPanel(); 
     container.setBackground(Color.white); 
     container.setBorder(
       BorderFactory.createCompoundBorder(new LineBorder(Color.BLACK), new EmptyBorder(10, 10, 10, 10))); 
     container.setMinimumSize(new Dimension(960, 400)); 
     container.setPreferredSize(new Dimension(960, 400)); 
     container.setLayout(new BoxLayout(container, BoxLayout.Y_AXIS)); 

     JPanel up = components.getUp(container); 
     container.add(up); 
     JPanel down = components.getDown(container); 
     container.add(down); 
     return container; 
    } 
} 

更接近你的原提案的另一種解決辦法是這樣的:

public abstract class CentralPage{ 

    private static CentralPage page; 

    protected JPanel container; 

    protected CentralPage(){ 
     container = new JPanel(); 
     container.setBackground(Color.white); 
     container.setBorder(
       BorderFactory.createCompoundBorder(new LineBorder(Color.BLACK), new EmptyBorder(10, 10, 10, 10))); 
     container.setMinimumSize(new Dimension(960, 400)); 
     container.setPreferredSize(new Dimension(960, 400)); 
     container.setLayout(new BoxLayout(container, BoxLayout.Y_AXIS)); 

     JPanel up = getUp(container); 
     container.add(up); 
     JPanel down = getDown(container); 
     container.add(down); 
    } 

    static JPanel getInstance(){ 
     if(page==null){ 
      page=new CentralPage(); 
     } 
     return page.getContainer(); 
    } 

    abstract JPanel getDown(JPanel container); 

    abstract JPanel getUp(JPanel container); 

    protected JPanel getContainer(){ 
     return this.container; 
    } 
} 

這樣做的缺點(而反模式)的方法是你需要記住在你的具體類上創建一個構造函數,調用super();

+0

我應該如何在「小孩」課上「叫」它? (類,它實現增減的) '靜態的JPanel的getInstance(){ \t返回CentralPage.getInstance(本); }'? –

+0

這是不可能的,因爲'this'在'static'方法中沒有意義。但是,爲什麼你想要在孩子班級中構建父母?你可能有一個更大的範圍內(如您的UI應用程序),你會叫'的JPanel的mainPanel = CentralPage.getInstance(新增減的(){/ *實現這兩種方法* /});' – Deroude

0

祝賀您閱讀「Effective Java」並試圖將其付諸實踐。它將爲您的代碼帶來更多的可用性和清晰度。

現在,讓我們來看看:

1.In首先,如果你的抽象CentralPage只需要在施工矩兩個Panel對象,最簡單的方法是非抽象類中的兩個參數其構造函數

public class CentralPage 
{ 
    public CentralPage(Panel up, Panel dn) 
    { 
     ... 
    } 
} 

2。如果在收到施工參數APPART,有一些行爲,是不知道的CentralPage,它必須在對象的生命週期內的任何時間(在構造函數中結束)委託給第三方,正確的模式將是的抽象類爲每個所需的行爲一個抽象方法:

public abstract class CentralPage 
{ 
    protected CentralPage(...) 
    { 
     ... 
    } 

    protected abstract return-type myBehaviour1(parameters...) 
    { 
     ... 
    } 

    protected abstract return-type myBehaviour2(parameters...) 
    { 
     ... 
    } 
} 

而且,科西嘉,每個非抽象子必須提供每個所需行爲implemeting其相應的方法。

3.Static工廠方法是針對非抽象類。它的目的是決定對象是否(在單件模式也許現有的對象可以重複使用,等等)要創建,並最終決定哪一個類必須被實例化(也許所有者類本身,或者可能一些子類)。