मैं ग्राहक अनुरोधों के प्रवाह को संसाधित करना चाहता हूं। प्रत्येक अनुरोध का विशेष प्रकार होता है। सबसे पहले मुझे उस प्रकार के लिए कुछ डेटा प्रारंभ करना होगा, और इसके बाद मैं अनुरोधों को संसाधित करना शुरू कर सकता हूं। जब क्लाइंट का प्रकार पहली बार आता है, तो मैं केवल इसी डेटा को प्रारंभ करता हूं। इसके बाद उस प्रकार के सभी अनुरोधों को उस डेटा का उपयोग करके संसाधित किया जाता है।क्या यह कोड थ्रेड-सुरक्षित है?
मुझे इसे थ्रेड-सुरक्षित तरीके से करने की आवश्यकता है।
यहां एक कोड लिखा है जो मैंने लिखा है। क्या यह धागा सुरक्षित है?
public class Test {
private static Map<Integer, Object> clientTypesInitiated = new ConcurrentHashMap<Integer, Object>();
/* to process client request we need to
create corresponding client type data.
on the first signal we create that data,
on the second - we process the request*/
void onClientRequestReceived(int clientTypeIndex) {
if (clientTypesInitiated.put(clientTypeIndex, "") == null) {
//new client type index arrived, this type was never processed
//process data for that client type and put it into the map of types
Object clientTypeData = createClientTypeData(clientTypeIndex);
clientTypesInitiated.put(clientTypeIndex, clientTypeData);
} else {
//already existing index - we already have results and we can use them
processClientUsingClientTypeData(clientTypesInitiated.get(clientTypeIndex));
}
}
Object createClientTypeData(int clientIndex) {return new Object();}
void processClientUsingClientTypeData(Object clientTypeData) {}
}
एक हाथ से, ConcurrentHashMap map.put (ए, बी) == ही ए के लिए अशक्त दो बार दूसरी ओर से, काम और comparisson आपरेशन थ्रेड-सुरक्षित नहीं है का उत्पादन नहीं कर सकते हैं।
तो क्या यह कोड ठीक है? यदि नहीं, तो मैं इसे कैसे ठीक कर सकता हूं?
अद्यतन: मैंने मार्टिन सेरानो का जवाब स्वीकार कर लिया है क्योंकि उसका कोड थ्रेड-सुरक्षित है और यह प्रारंभिक समस्या को डबल करने के लिए प्रवण नहीं है। लेकिन मुझे यह ध्यान रखना होगा कि मुझे अपने संस्करण के साथ कोई भी जारी नहीं मिला है, जो नीचे दिए गए उत्तर के रूप में पोस्ट किया गया है, और मेरे संस्करण को सिंक्रनाइज़ेशन की आवश्यकता नहीं है।
मुझे लगता है कि आपको 'processClientUsingClientTypeData' से पहले 'else' की आवश्यकता है। – Gray
यह थ्रेड-सुरक्षित भी नहीं है! देखो: एक धागा मिल कार्यान्वित करता है, अशक्त के खिलाफ तुलना, चरणों में है, तो एक और धागा एक ही होता है, तो एक clientTypeData को प्रदान करती है और अंत में विधि से देता है, लेकिन एक और धागा clientTypeData ओवरराइड करता है। –
@ krzysztof असुरक्षित क्या है? जैसे मैंने कहा, _if_ आप कभी-कभी CreateClientTypeData को एक से अधिक बार निष्पादित करने पर ध्यान नहीं देते हैं, यह ठीक है। यदि आप वर्णन करते हैं, तो दूसरा धागा परिणाम को पहले स्थान से बदल देगा। संभवतः चूंकि कोई भी अनुरोध प्रारंभिकरण को ट्रिगर कर सकता है, तो यह हर बार एक ही परिणाम देगा। यदि प्रारंभिकता _really_ महंगा है, तो उससे बचने के लिए और अधिक जटिलता जोड़ा जा सकता है। –