2012-11-01 27 views
2

我有一個Java中的情況,我有一個方法返回一個InputStream,並且我想讓它使得每當該人調用該InputStream上的close函數時,代碼得到通知(如回調)。InputStream與Java中的「事件」

但是,我返回的實際InputStream是由庫調用返回的InputStream的子類,所以我沒有直接控制它。

我目前的解決方案是創建一個InputStream的子類,它有一個InputStream成員變量,它由構造函數中的庫調用實例化,我只是重寫InputStream的方法,並讓它們使用變量的方法close()函數做了額外的事情。

這有效,但我想減少必須創建一個全新的類的開銷,重寫所有必要的方法,以便我可以在調用close()時執行單個事件。

回答

1

您可以使用Java bean事件機制來做到這一點。

http://docs.oracle.com/javase/tutorial/javabeans/writing/events.html

這假設聽衆和廣播在同一個JVM運行。

這是我腦子裏想的:

package io; 

import java.beans.PropertyChangeListener; 
import java.beans.PropertyChangeSupport; 
import java.io.IOException; 
import java.io.InputStream; 

/** 
* BroadcastingInputStream broadcasts to interested listeners when it closes. 
* @author Michael 
* @since 10/31/12 8:34 PM 
* @link http://stackoverflow.com/questions/13169206/possible-in-java-to-create-an-event-when-a-function-is-called-on-a-particular-ob/13169271#comment17920062_13169271 
*/ 
public class BroadcastingInputStream extends InputStream { 

    private InputStream is; 
    private PropertyChangeSupport propertyChangeSupport; 

    public BroadcastingInputStream(InputStream is) { 
     this.is = is; 
     this.propertyChangeSupport = new PropertyChangeSupport(this); 
    } 

    @Override 
    public int read() throws IOException { 
     return this.is.read(); 
    } 

    public void addCloseListener(PropertyChangeListener closeListener) { 
     this.propertyChangeSupport.addPropertyChangeListener(closeListener); 
    } 

    public void removeCloseListener(PropertyChangeListener closeListener) { 
     this.propertyChangeSupport.removePropertyChangeListener(closeListener); 
    } 

    @Override 
    public void close() throws IOException { 
     super.close(); 
     this.propertyChangeSupport.firePropertyChange("closed", false, true); 
    } 
} 
+0

我不認爲你明白這個問題。他希望避免創建InputStream的整個子類並對所有方法進行傳遞。 OP,對不起,沒有看到更簡單的方法。至少只有7種左右的方法... – arcy

+0

我想我的確誤解了。我會刪除。 – duffymo

3

阿帕奇百科全書IO有多種過濾I/O流,使得它很容易做你描述的。

+0

我在該庫中找到了AutoCloseInputStream,這對我所需要的非常有用,謝謝! –

3

如果你希望它對InputStream的用戶透明,你幾乎必須這樣做。也就是說,你不需要自己編寫所有的代碼,因爲FilterInputStream爲你做了所有的基本工作(你只需要重寫close()方法)。

+0

與@bmarguiles混合使用答案,['org.apache.commons.io.input.ProxyInputStream'](http://commons.apache.org/io/api-release/org/apache/commons/io/input/ ProxyInputStream.html)是「FilterInputStream」的擴展 – madth3