2014-11-20 22 views
3

可調用的拋出異常,Runnable不。是否有標準的Java 8 FunctionalInterface用於引發檢查異常的塊?

有什麼標準,看起來像

@FunctionalInterface 
public interface TypedBlock<E extends Exception> { 
    public void run() throws E; 
} 
+1

沒有AFAIK。 'Callable '和'return null;'。 – 2014-11-20 22:00:27

+0

請注意,實現者可自行定義更多受限的異常類型:'class MyCallable implements Callable {public Void call()throws IOException {...}} ==「我只會拋出IOExceptions」 – 2014-11-20 22:04:50

+0

返回null是一個在與lambdas和方法參考對接疼痛。 – 2014-11-20 22:05:19

回答

3

沒有,有沒有內置的功能,我知道。但是,您可以使用外部庫(以及許多其他很酷的功能)。

您可以使用JOOL,您可以在此處使用Unchecked類。

從那裏頁面的例子說明了這一點與IOException

Arrays.stream(dir.listFiles()).forEach(
    Unchecked.consumer(file -> { System.out.println(file.getCanonicalPath()); }) 
); 

另一個(在我看來更好)的方法是使用功能的設計圖書館像Functionaljava

如果結果成功,一個好方法是將您的任務包裝在Validation之後再決定。這可能是這樣的:

TypedBlock<IOException> foo = ...; 

// do your work 
final Validation<IOException, Unit> validation = Try.f(() -> { 
    foo.run(); 
    return Unit.unit(); // Unit equals nothing in functional languages 
})._1(); 

// check if we got a failure 
if (validation.isFail()) { 
    System.err.println("Got err " + validation.fail()); 
} 

// check for success 
if (validation.isSuccess()) { 
    System.out.println("All was good :-)"); 
} 

// this will just print out a message if we got no error 
validation.forEach(unit -> System.out.println("All was good")); 
2

java.lang.AutoCloseable具有()->{} throws Exception簽名,但是,它是一個預定義的語義負擔。所以對於臨時使用它可能是合適的,但是當你設計一個API時,我建議定義你自己的interface

請注意,您的專用接口,還可以擴展Callable<Void>是一個標準的interface

interface Block<E extends Exception> extends Callable<Void>{ 
    void run() throws E; 
    @Override default Void call() throws E { run(); return null; } 
    /** This little helper method avoids type casts when a Callable is expected */ 
    static <T extends Exception> Block<T> make(Block<T> b) { return b; } 
} 

這樣,您就可以使用您Block接口與現有的API:

// Example 
ExecutorService e=Executors.newSingleThreadExecutor(); 
try { 
    e.submit(Block.make(()->{ throw new IOException("test"); })).get(); 
} catch (InterruptedException ex) { 
    throw new AssertionError(ex); 
} catch (ExecutionException ex) { 
    System.out.println("received \""+ex.getCause().getMessage()+'"'); 
} 
e.shutdown(); 

注意與訣竅靜態方法Block.make。沒有它,你將不得不將lambda表達式轉換爲(Block<IOException>),而不是從改進的類型推斷中獲益。只有在期望Callable的情況下,對於預期爲Block的您自己的API,您可以直接使用lambda表達式和方法引用。

相關問題