कोई Memoization के लिए निर्मित है जावा समारोह है, हालांकि यह बहुत मुश्किल, इसे लागू करने के इस तरह उदाहरण के लिए, नहीं है:
public static <T> Supplier<T> memoize(Supplier<T> delegate) {
AtomicReference<T> value = new AtomicReference<>();
return() -> {
T val = value.get();
if (val == null) {
val = value.updateAndGet(cur -> cur == null ?
Objects.requireNonNull(delegate.get()) : cur);
}
return val;
};
}
ध्यान दें कि विभिन्न कार्यान्वयन दृष्टिकोण मौजूद हैं। उपर्युक्त कार्यान्वयन प्रतिनिधि को कई बार कॉल कर सकता है यदि ज्ञापन सप्लायर विभिन्न धागे से कई बार अनुरोध करता है। कभी-कभी लॉक के साथ स्पष्ट सिंक्रनाइज़ेशन पर ऐसे कार्यान्वयन को प्राथमिकता दी जाती है। ताला पसंद किया जाता है, तो DCL इस्तेमाल किया जा सकता है:
public static <T> Supplier<T> memoizeLock(Supplier<T> delegate) {
AtomicReference<T> value = new AtomicReference<>();
return() -> {
T val = value.get();
if (val == null) {
synchronized(value) {
val = value.get();
if (val == null) {
val = Objects.requireNonNull(delegate.get());
value.set(val);
}
}
}
return val;
};
}
यह भी ध्यान रखें, के रूप में @LouisWasserman सही ढंग से टिप्पणी में उल्लेख किया है, तो आप आसानी से अमरूद आपूर्तिकर्ता में JDK आपूर्तिकर्ता बदल सकता है और इसके विपरीत विधि संदर्भ का उपयोग करते हुए:
java.util.function.Supplier<String> jdkSupplier =() -> "test";
com.google.common.base.Supplier<String> guavaSupplier = jdkSupplier::get;
java.util.function.Supplier<String> jdkSupplierBack = guavaSupplier::get;
तो गुवा और जेडीके कार्यों के बीच स्विच करने की कोई बड़ी समस्या नहीं है।
स्रोत
2016-02-11 06:44:06
बिल्कुल नहीं, लेकिन आप अंत में ':: get' लिखकर j.u.f.Suppliers और c.g.c.b.Suppliers के बीच आसानी से परिवर्तित कर सकते हैं। –
@LouisWasserman के रूप में सुझाव देता है, आप मूल रूप से "वापसी Suppliers.memoize (प्रतिनिधि :: प्राप्त) :: प्राप्त करने के द्वारा guava Suppliers :: memoize के लिए एक रैपर बना सकते हैं;" – jvdneste
यह निश्चित रूप से एक दयालुता है कि Suppliers.memoize ने इसे jdk8 मानक लाइब्रेरी में नहीं बनाया है, क्योंकि यह मेरे लिए बहुत कम जोखिम वाले जोखिम की तरह लगता है। – jvdneste