2013-08-18 7 views
11

मुझे लगता है कि जब तक एप्लिकेशन चल रहा है एक नियमित आधार पर एक सर्वर के साथ संचार एक Android एप्लिकेशन का निर्माण कर रहा हूँ का उपयोग कर एक सर्वर के साथ संवाद करने के लिए।एंड्रॉयड ग्राहक के लिए सबसे अच्छा अभ्यास धागे

मैं जब अनुप्रयोग शुरू होता है, तो मैं संदेशों ReceiverThread कहा जाता प्राप्त करने के लिए एक अलग thread है सर्वर से कनेक्शन की प्रक्रिया शुरू करके ऐसा करते हैं, इस threadsocket से संदेश पढ़ता है, यह विश्लेषण करती है, और उचित हिस्सा को फ़ॉरवर्ड आवेदन के एक पाश में

यह thread रन, पढ़ने जब तक नए डेटा आता है जो कुछ भी यह read() आदेश पर ब्लॉक पढ़ सकते हैं और उसके बाद के लिए है, तो यह खर्च करता है इसमें से अधिकांश समय ब्लॉक किया गया है।

मैं एक अलग धागे के माध्यम से संदेश भेजने संभाल, SenderThread कहा जाता है। मैं किस बारे में सोच रहा हूं: क्या मुझे एक ही फैशन में SenderThread बनाना चाहिए? मतलब मैं किसी न किसी रूप, इस सूत्र के लिए एक कतार बनाए रखना चाहिए यह कतार में सभी संदेशों को भेजने के लिए और तब तक नए संदेश कतार में प्रवेश अवरुद्ध करने देते, या मैं बस हर बार संदेश भेजे जाने की आवश्यकता धागा का एक नया उदाहरण शुरू कर देना चाहिए , इसे संदेश भेज दें और फिर "मर जाएं"? मैं पहले दृष्टिकोण की तरफ झुका रहा हूं, लेकिन मुझे नहीं पता कि प्रदर्शन की अवधि में क्या वास्तव में बेहतर है (स्मृति में अवरुद्ध थ्रेड को बनाम नए धागे को शुरू करने के विरुद्ध), और कोड शुद्धता के मामले में।

चूंकि मेरी सभी गतिविधियों को संदेश भेजने और प्राप्त करने में सक्षम होने की आवश्यकता है, इसलिए मैं अपने Application कक्षा में दोनों धागे का संदर्भ रख रहा हूं, क्या यह एक स्वीकार्य दृष्टिकोण है या मुझे इसे अलग-अलग कार्यान्वित करना चाहिए?

एक समस्या यह है कि मैं इस के साथ सामना करना पड़ा है कि मैं वास्तव ReceiverThread के दो उदाहरणों है कभी कभी अगर मैं अपने आवेदन को बंद करने और इसे फिर से चलाने है, इसलिए मैं दो बार कुछ संदेश मिलता है।

मैं अनुमान लगा रहा हूँ कि इस वजह से अपने आवेदन वास्तव में बंद नहीं किया और पिछले धागा अभी भी सक्रिय था (read() संचालन पर अवरुद्ध), और जब मैं आवेदन फिर से खोला एक नया धागा प्रारंभ किया गया था, लेकिन दोनों से जुड़े थे सर्वर इसलिए सर्वर ने दोनों को संदेश भेजा। इस समस्या को हल करने के तरीके, या इसे पूरी तरह व्यवस्थित करने के तरीके पर कोई सुझाव, तो यह सही होगा?

मैं इन सवालों को देख कोशिश की, लेकिन मेरा पहला प्रश्न के लिए कुछ परस्पर विरोधी उदाहरण मिल गया है, और कुछ भी नहीं है कि पर्याप्त रूप से उपयोगी है और मेरे दूसरे प्रश्न पर लागू होता है ...

+0

में मदद करता है "बंद" ऐप वास्तव में इसे मार नहीं रहा है। यह सिर्फ चल रहा है और विशेष रूप से धागे किसी भी तरह से – zapl

+0

@zapl को रोक नहीं है हाँ, मुझे इसकी जानकारी है, यह मेरी समस्या है। सवाल यह है कि धागे को विश्वसनीय रूप से कैसे रोकें? या इस समग्र समस्या को इस तरीके से कैसे बचाया जा सकता है? – Bob

+0

यह वास्तव में मुश्किल है। 'थ्रेड # इंटरप्ट() '(+' सॉकेट # क्लोज़() ') का उपयोग इसे रोकने के लिए किया जा सकता है लेकिन कठिन हिस्सा यह ट्रैक रखना है कि एप्लिकेशन चल रहा है या पृष्ठभूमि में बस निष्क्रिय है या नहीं। उदाहरण के लिए प्रत्येक गतिविधि 'ऑनस्टार्ट' पर 'ऑनस्टार्ट' से कर सकती है। – zapl

उत्तर

17

1. आपका दृष्टिकोण है, ठीक है अगर तुम वास्तव में को हर समय सर्वर और क्लाइंट के बीच एक खुला कनेक्शन रखने की आवश्यकता है। हालांकि मैं एक एसिंक्रोनस कनेक्शन का उपयोग करूंगा, जैसे सर्वर पर HTTP अनुरोध भेजना और जब भी सर्वर ऐसा लगता है तो एक उत्तर प्राप्त करें।

यदि आपको कुछ समय बाद क्लाइंट को जवाब देने के लिए सर्वर की आवश्यकता है, लेकिन आप नहीं जानते कि कब, आप Google Cloud Messaging framework पर भी देख सकते हैं, जो आपको अपने ग्राहकों को छोटे संदेश भेजने का एक पारदर्शी और सुसंगत तरीका देता है आपके सर्वर से

आप कुछ बातों पर विचार करना है जब आप एक मोबाइल अनुप्रयोग विकसित कर रहे हैं की जरूरत है।

  1. एक स्मार्टफोन बैटरी की अंतहीन राशि नहीं है।

  2. में स्मार्ट फ़ोन के इंटरनेट कनेक्शन कुछ हद तक अस्थिर है और आप अलग अलग समय पर इंटरनेट कनेक्शन खो देंगे।

जब आप सर्वर के लिए एक सीधा संबंध हर समय रखने के लिए, अपने अनुप्रयोग जिसका मतलब है कि आप चूसना किए जाने वाले फ़ोन बहुत तेजी से सुखाने के जीवित-रखें पैकेट भेजने रखने के लिए,। जब इंटरनेट कनेक्शन मोबाइल ब्रॉडबैंड पर पहुंचने योग्य अस्थिर है, तो आप कभी-कभी कनेक्शन खो देंगे और इससे पुनर्प्राप्त करने की आवश्यकता होगी। तो यदि आप TCP का उपयोग करते हैं क्योंकि आप यह सुनिश्चित करना चाहते हैं कि आपके पैकेट प्राप्त हो जाएं तो आपको एक ही पैकेट को कई बार फिर से भेजना होगा और इसलिए बहुत अधिक ओवरहेड प्राप्त करें।

यदि आप सर्वर पर थ्रेड खोलते हैं, तो यह सर्वर की तरफ थ्रेडिंग समस्याओं में भी हो सकता है, जो ऐसा लगता है। मान लें कि आपके पास एक ही समय में सर्वर से कनेक्ट होने वाले 200 क्लाइंट हैं। प्रत्येक ग्राहक के पास सर्वर पर 1 धागा खुलता है। यदि सर्वर को एक ही समय में 200 अलग-अलग धागे की सेवा करने की आवश्यकता है, तो यह सर्वर के अंत में काफी प्रदर्शन करने वाला कार्य हो सकता है और आपको अपने आप पर भी बहुत कुछ करने की आवश्यकता होगी।

2. जब आप अपने आवेदन से बाहर निकलेंगे, तो आपको अपने बाद साफ-सफाई करने की आवश्यकता होगी। यह आपके Activity की विधि में किया जाना चाहिए जो सक्रिय है।

इसका मतलब है कि, अपने यूआई की स्थिति को बचाने के लिए सभी सक्रिय धागे (या कम से कम उन्हें इंटरप्ट करना) को मारना, यदि आपको इसकी आवश्यकता है) और आपके पास सर्वर के जो भी खुले कनेक्शन बंद हो रहे हैं और बंद कर रहे हैं।

जहां तक ​​Threads का उपयोग किया जाता है, मैं Handlers जैसे कुछ बिल्ड-इन थ्रेडिंग टूल का उपयोग करने या AsyncTask को लागू करने की अनुशंसा करता हूं।

यदि आपको वास्तव में लगता है कि Thread जाने का तरीका है, तो मैं निश्चित रूप से Singleton pattern को अपने थ्रेडिंग के लिए "प्रबंधक" के रूप में उपयोग करने की अनुशंसा करता हूं।

यह प्रबंधक आपके धागे को नियंत्रित करेगा, इसलिए आप किसी भी समय सर्वर से बात करते हुए एक से अधिक Thread के साथ समाप्त नहीं होते हैं, भले ही आप एप्लिकेशन के किसी अन्य भाग में हों। जो लोग वैश्विक आवेदन राज्य बनाए रखने की जरूरत के लिए

बेस वर्ग:

जहाँ तक Application वर्ग कार्यान्वयन चला जाता है के रूप में, Application class documentation पर एक नज़र डालें। आप अपने एंड्रॉइडManifest.xml के टैग में अपना नाम निर्दिष्ट करके अपना स्वयं का कार्यान्वयन प्रदान कर सकते हैं, जिससे आपके क्लास/पैकेज के लिए प्रक्रिया बनाई जाने पर उस कक्षा को आपके लिए तत्काल चालू किया जाएगा।

सामान्य रूप से एप्लिकेशन को उपclass करने की आवश्यकता नहीं है। ज्यादातर स्थितियों में, स्थिर सिंगलेट्स एक ही कार्यक्षमता को अधिक मॉड्यूलर तरीके से प्रदान कर सकते हैं।

तो अपने स्वयं के Application वर्ग को लागू करने से दूर रखना की सिफारिश की है, फिर भी अगर आप अपने Activities में से एक Threads और कनेक्शन आप (बस हो सकता है) मुसीबत में पड़ सकता है के प्रबंधन के लिए अपने स्वयं के Singleton वर्ग को प्रारंभ करते हैं, क्योंकि आरंभीकरण सिंगलटन के विशिष्ट Activity पर "बाध्य" हो सकता है और इसलिए यदि विशिष्ट Activity स्क्रीन से हटा दिया गया है और रोका गया है तो इसे मार दिया जा सकता है और इसलिए सिंगलटन भी मारे जा सकता है। तो आपके Application कार्यान्वयन के अंदर सिंगलटन को प्रारंभ करना उपयोगी समझा जा सकता है।

पाठ की दीवार के लिए क्षमा करें, लेकिन आपके सवाल का काफी "ओपन एंडेड" है, इसलिए मैं आप कुछ हद तक एक ओपन एंडेड सवाल देने के लिए कोशिश की है - आशा है कि यह ;-)

+0

धन्यवाद, हालांकि मैं अभी भी पूरी तरह से सुनिश्चित नहीं हूं कि वास्तव में क्या करना है, आपके उत्तर ने मदद की है। मुझे पता है कि मोबाइल फोन के विकास के लिए बैटरी जीवन को संरक्षित करने जैसे कई पहलू हैं, हालांकि ऐप के मेरे उपयोग के मामले में मुझे निरंतर कनेक्शन की आवश्यकता है। ऐप का उपयोग आम तौर पर छोटा होना चाहिए, आमतौर पर 5 मिनट पर्याप्त से अधिक होता है, हालांकि उन 5 मिनट के दौरान इंटरनेट पर कई इंटरैक्शन होना चाहिए। मुझे सच में नहीं लगता कि 5 मिनट के लिए जिंदा कनेक्शन रखने से बैटरी सूखी हो जाएगी, है ना? – Bob

+0

@Bob 5 मिनट ठीक है। पृष्ठभूमि में नियमित अद्यतन समस्याग्रस्त हैं। http://developer.android.com/training/efficient-downloads/index.html देखें – zapl

संबंधित मुद्दे