7 回答
TA貢獻(xiàn)1828條經(jīng)驗(yàn) 獲得超13個(gè)贊
永遠(yuǎn)不會(huì)調(diào)用流orElse,但會(huì)執(zhí)行方法本身。這意味著方法參數(shù)也傳遞給它。Optional.ofNullable(t).orElseThrow(() -> new Exception("MyException"))因此無(wú)論傳遞給第一次調(diào)用的值如何,都會(huì)調(diào)用該部分Optional.ofNullable。
如果你不希望這種情況發(fā)生,你需要傳遞Supplier這樣的信息:
String t = null;
Optional.ofNullable("notnull")
.orElseGet(
() -> Optional.ofNullable(t).orElseThrow(() -> new RuntimeException("MyException"))
);
orElseGet只有在調(diào)用流時(shí)才會(huì)調(diào)用供應(yīng)商。請(qǐng)注意,您需要一個(gè)RuntimeException而不是已檢查的異常才能脫離供應(yīng)商。
TA貢獻(xiàn)1824條經(jīng)驗(yàn) 獲得超5個(gè)贊
那是因?yàn)槔锩娴拇aorElse()總是會(huì)被評(píng)估。換句話說(shuō),即使您指定非空,它也會(huì)被執(zhí)行Optional,所以這就是Exception拋出的原因。
如果您查看Java 可選 – orElse() 與 orElseGet()orElse()文章的部分,您可以在他們的示例中看到這一點(diǎn),其中顯示:
我們可以很容易地推斷出 orElse() 的參數(shù)即使在具有非空 Optional 的情況下也會(huì)被評(píng)估。
TA貢獻(xiàn)1820條經(jīng)驗(yàn) 獲得超9個(gè)贊
我真的很想知道為什么這段代碼是以這種方式編寫的。似乎它需要觸發(fā)一個(gè)異常,并在可選中添加一個(gè)顯式的 NULL 值。
正如已經(jīng)說(shuō)過(guò)的,當(dāng)使用orElse()而不是orElseGet()方法時(shí),無(wú)論 T 的值如何(例如Optional<T>)都會(huì)被評(píng)估。
我會(huì)使用更好的時(shí)尚和理解:
String value = "notnull"; // could be null
Optional.ofNullable(value)
.orElseThrow(MyException::new);
如果值為 NULL,則會(huì)觸發(fā)異常。
注意:您可以使用方法引用來(lái)調(diào)用異常
TA貢獻(xiàn)2039條經(jīng)驗(yàn) 獲得超8個(gè)贊
你寫的是這樣的:
String t = null;
String myException = Optional.ofNullable(t).orElseThrow(() -> new Exception("MyException"));
Optional.ofNullable("notnull").orElse(myException);
在您知道您的值是否為空之前,部分已被評(píng)估。如果您想要評(píng)估,請(qǐng)考慮orElse方法。Optional"Lazy"orElseGet
TA貢獻(xiàn)1804條經(jīng)驗(yàn) 獲得超8個(gè)贊
關(guān)于Optional ,您應(yīng)該注意以下幾點(diǎn):
如果已知被包裝的值是否為空,請(qǐng)使用Optional.of()或Optional.empty()。如果不確定(例如值是從其他地方獲得的變量),請(qǐng)使用Optional.ofNullable()
Optional.orElse()和Optional.orElseGet()之間有一個(gè)重要的區(qū)別。
orElse接受一個(gè)已經(jīng)計(jì)算出的值,如果提供了一個(gè)表達(dá)式,它會(huì)立即執(zhí)行并立即計(jì)算。這發(fā)生在有問(wèn)題的代碼中。因此,這個(gè) else 變體應(yīng)該用于已經(jīng)可用的值或原語(yǔ)。orElseGet接受一個(gè)供應(yīng)商函數(shù),該函數(shù)僅在評(píng)估可選鏈并請(qǐng)求替代值時(shí)運(yùn)行。當(dāng)替代值的生成或計(jì)算成本昂貴時(shí)應(yīng)使用此方法。
// Fine
Optional<String> name = Optional.of(someValue).orElse("defaultName");
// But this:
Optional<String> name = Optional.of(someValue).orElse(db.queryName());
// Is better written as following, as it saves you from an expensive operation
Optional<String> name = Optional.of(someValue).orElseGet(() -> db.queryName());
TA貢獻(xiàn)1859條經(jīng)驗(yàn) 獲得超6個(gè)贊
問(wèn)題是按執(zhí)行順序。它嘗試計(jì)算 .orElse(...) 的值并在 .orElseThrow 上拋出 MyException。
換句話說(shuō),如果 t 不為空,執(zhí)行流程如下:
1) 計(jì)算值
Optional.ofNullable(t).orElseThrow(() -> new Exception("MyException"))2) 使用 (1) 中的值
Optional.ofNullable("notnull").orElse(...)TA貢獻(xiàn)1833條經(jīng)驗(yàn) 獲得超4個(gè)贊
結(jié)果是預(yù)料之中的,因?yàn)樵?Java 中,在調(diào)用帶有參數(shù)的方法之前,JVM 之前所做的事情是評(píng)估參數(shù)值。
那就是調(diào)用的參數(shù)值.orElse():
Optional.ofNullable(t).orElseThrow(() -> new Exception("MyException"))由于t引用null,因此預(yù)計(jì)會(huì)拋出異常。
添加回答
舉報(bào)
