मनमाने ढंग से बड़ी संख्या में कार्य पूरा होने के लिए जावा सिंक्रनाइज़ेशन ऑब्जेक्ट का उपयोग करना चाहिए? बाधाएं हैं:सभी कार्यों को पूरा करने के लिए सिंक्रनाइज़ेशन ऑब्जेक्ट
- प्रत्येक कार्य को पूरा करने के लिए एक गैर-तुच्छ राशि लेती है और समानांतर में कार्य करने के लिए उपयुक्त है।
- स्मृति में फिट करने के लिए बहुत सारे कार्य हैं (यानी मैं को प्रत्येक कार्य के लिए
Collection
में नहीं डाल सकता और फिर सभी वायदा परget
पर कॉल कर सकता हूं)। - मुझे नहीं पता कि कितने कार्य होंगे (यानी मैं
CountDownLatch
का उपयोग नहीं कर सकता)। ExecutorService
तो साझा किया जा सकता मैंawaitTermination(long, TimeUnit)
उदाहरण के लिए, उपयोग नहीं कर सकते ग्रांड सेंट्रल डिस्पैच के साथ, मैं कुछ इस तरह कर सकते हैं:
let workQueue = dispatch_get_global_queue(QOS_CLASS_BACKGROUND, 0)
let latch = dispatch_group_create()
let startTime = NSDate()
var itemsProcessed = 0
let countUpdateQueue = dispatch_queue_create("countUpdateQueue", DISPATCH_QUEUE_SERIAL)
for item in fetchItems() // generator returns too many items to store in memory
{
dispatch_group_enter(latch)
dispatch_async(workQueue)
{
self.processItem(item) // method takes a non-trivial amount of time to run
dispatch_async(countUpdateQueue)
{
itemsProcessed++
}
dispatch_group_leave(latch)
}
}
dispatch_group_wait(latch, DISPATCH_TIME_FOREVER)
let endTime = NSDate()
let totalTime = endTime.timeIntervalSinceDate(startTime)
print("Processed \(itemsProcessed) items in \(totalTime) seconds.")
यह उत्पादन है कि (के लिए इस तरह दिखता है पैदा करता है 128 आइटम): Processed 128 items in 1.846794962883 seconds.
मैं एक Phaser
साथ कुछ इसी तरह की कोशिश की:
final Executor executor = new ThreadPoolExecutor(64, 64, 1l, MINUTES, new LinkedBlockingQueue<Runnable>(8), new CallerRunsPolicy());
final Phaser latch = new Phaser(0);
final long startTime = currentTimeMillis();
final AtomicInteger itemsProcessed = new AtomicInteger(0);
for(final String item : fetchItems()) // iterator returns too many items to store in memory
{
latch.register();
final Runnable task = new Runnable() {
public void run() {
processItem(item); // method takes a non-trivial amount of time to run
itemsProcessed.incrementAndGet();
latch.arrive();
}
};
executor.execute(task);
}
latch.awaitAdvance(0);
final long endTime = currentTimeMillis();
out.println("Processed " + itemsProcessed.get() + " items in " + (endTime - startTime)/1000.0 + " seconds.");
कार्य करने के हमेशा पूरा नहीं हुआ पिछले प्रिंट बयान से पहले और मैं उत्पादन है कि इस तरह दिखता है मिल सकता है (128 मदों के लिए): Processed 121 items in 5.296 seconds.
Phaser
भी सही उपयोग करने के लिए वस्तु है? दस्तावेज इंगित करता है कि यह केवल 65,535 पार्टियों का समर्थन करता है, इसलिए मुझे या तो प्रक्रियाओं को संसाधित करने या Phaser
स्तरीय प्रकार के परिचय देने की आवश्यकता होगी।
जब आप कहते हैं कि स्मृति में फिट करने के लिए बहुत सारे कार्य हैं तो क्या यह संसाधन बाधा नहीं है? तो आप समान रूप से उन कार्यों को निष्पादित कर सकते हैं जो स्मृति में फिट होते हैं और आप इसके लिए भविष्य का उपयोग कर सकते हैं। सुनिश्चित नहीं है कि कोई दृष्टिकोण पास संसाधन प्रदूषण को पार करने में मदद करेगा और आप एक बहुत ही जटिल समाधान के साथ समाप्त हो जाएंगे। – Lokesh