getApplication () বনাম get get অ্যাপ্লিকেশন কনটেক্সট ()


417

আমি এই এক সন্তোষজনক উত্তর, তাই এটি হলো খুঁজে পাইনি আমরা যেতে কি সঙ্গে চুক্তি Activity/Service.getApplication()এবং Context.getApplicationContext()?

আমাদের প্রয়োগে, উভয়ই একই বস্তুটি ফেরত দেয়। একটি ইন ActivityTestCaseতবে আবেদন উপহাস করতে হবে getApplication()উপহাস সঙ্গে ফিরে আসা, কিন্তু getApplicationContextএখনও একটি ভিন্ন প্রেক্ষাপটে উদাহরণস্বরূপ (এক Android দ্বারা ইনজেকশনের) ফিরে আসবে। এটা কি বাগ? এটা উদ্দেশ্য হয়?

আমি প্রথম স্থানের পার্থক্যটিও বুঝতে পারি না। কোনও টেস্ট স্যুইটের বাইরে এমন কি মামলা রয়েছে যেখানে উভয় কলই আবার বিভিন্ন বস্তুর সাথে ফিরে আসতে পারে? কখন এবং কেন? তদতিরিক্ত, কেন এবং getApplicationউপর সংজ্ঞায়িত করা হয় , কিন্তু না ? সর্বদা কোথাও থেকে কোনও বৈধ অ্যাপ্লিকেশন উদাহরণ পাওয়া উচিত নয় ?ActivityServiceContext


8
দুর্দান্ত প্রশ্ন। পরীক্ষার স্টাফগুলি কিছুটা রহস্য (যেমন আপনি ভাল জানেন)। তবে আমি অবাক হয়েছি যে আপনি যদি নিজের অ্যাপ্লিকেশনটিতে স্পষ্টভাবে কোনও বস্তু তৈরি না করেন তবে এই দুটি পদ্ধতি কলগুলিতে কোনও পার্থক্য দেখা দেয় Application
ক্রিস্টোফার অর

উত্তর:


366

খুব মজার প্রশ্ন। আমি মনে করি এটি মূলত একটি অর্থপূর্ণ অর্থ, এবং এটি historicalতিহাসিক কারণেও হতে পারে।

যদিও বর্তমান অ্যান্ড্রয়েড ক্রিয়াকলাপ এবং পরিষেবা বাস্তবায়নে, getApplication()এবং getApplicationContext()একই জিনিসটি ফেরত দেয়, এমন কোনও গ্যারান্টি নেই যে এটি সর্বদা ঘটবে (উদাহরণস্বরূপ, কোনও নির্দিষ্ট বিক্রেতা বাস্তবায়নে)।

সুতরাং আপনি যদি ম্যানিফেস্টে নিবন্ধিত অ্যাপ্লিকেশন শ্রেণিটি চান তবে আপনার কল করে কখনইgetApplicationContext() এটি আপনার অ্যাপ্লিকেশনটিতে কাস্ট করা উচিত নয় , কারণ এটি অ্যাপ্লিকেশন উদাহরণ হতে পারে না (যা আপনি পরীক্ষার কাঠামোর সাথে স্পষ্টতই অভিজ্ঞতা পেয়েছিলেন)।

কেন getApplicationContext()প্রথম স্থানে আছে?

getApplication()কেবলমাত্র ক্রিয়াকলাপ শ্রেণি এবং পরিষেবা শ্রেণিতে উপলভ্য, যেখানে getApplicationContext()প্রসঙ্গ শ্রেণিতে ঘোষণা করা হয়েছে।

এর প্রকৃত অর্থ একটি জিনিস: যখন কোনও ব্রডকাস্ট রিসিভারে কোড লেখার সময়, যা কোনও প্রসঙ্গ নয় তবে তার অন-রিসিভ পদ্ধতিতে একটি প্রসঙ্গ দেওয়া হয়, আপনি কেবল কল করতে পারেন getApplicationContext()। যার অর্থ হ'ল ব্রডকাস্টার্সিভারে আপনার অ্যাপ্লিকেশনটিতে অ্যাক্সেস পাওয়ার নিশ্চয়তা নেই।

অ্যান্ড্রয়েড কোডটি দেখার সময় আপনি দেখতে পাবেন যে সংযুক্ত থাকাকালীন কোনও ক্রিয়াকলাপটি একটি বেস প্রসঙ্গ এবং একটি অ্যাপ্লিকেশন গ্রহণ করে এবং সেগুলি বিভিন্ন পরামিতি। getApplicationContext()প্রতিনিধিদের এটি কল baseContext.getApplicationContext()

আরও একটি জিনিস: ডকুমেন্টেশনটি বলছে যে এটি বেশিরভাগ ক্ষেত্রেই আপনার সাবক্লাস অ্যাপ্লিকেশন প্রয়োজন হবে না:

সাধারণত সাবক্লাস করার প্রয়োজন নেই Application। বেশিরভাগ পরিস্থিতিতে স্থিতিশীল সিঙ্গলেটগুলি আরও কার্যকরভাবে একই কার্যকারিতা সরবরাহ করতে পারে। যদি আপনার সিঙ্গলটনের কোনও বৈশ্বিক প্রসঙ্গের প্রয়োজন হয় (উদাহরণস্বরূপ ব্রডকাস্ট রিসিভারগুলি নিবন্ধিত করতে), এটি পুনরুদ্ধার করার জন্য ফাংশনটি প্রথমে সিঙ্গেলটন নির্মাণের সময় Contextঅভ্যন্তরীণভাবে ব্যবহার করা যেতে পারে Context.getApplicationContext()

আমি জানি এটি একটি সঠিক এবং সুনির্দিষ্ট উত্তর নয়, তবে এখনও, এটি কি আপনার প্রশ্নের উত্তর দেয়?


89
@ পাইওয়াï: ডকটি শুনবেন না। সাবক্লাসিং android.app.Applicationসুপার হেল্প পূর্ণ। উদাহরণস্বরূপ আমার ডাটাবেসটি আরম্ভ করার অবিরাম সমস্যা ছিল। একবার Application.onCreateএটি সরানো একটি কবজ মত কাজ করে। এখন আমি সমস্ত সিস্টেমে প্রশস্ত সূচনাটি Applicationকরি এবং আমি ছাড়া আর একটি অ্যাপ লিখতে চাই না।
মার্টিন

9
@ মার্টিন ডকস না শুনে সাধারণত বোঝা যায় যে ভবিষ্যতে আপনার কোডটি ভেঙে যেতে পারে, বা এখনও অপ্রত্যাশিত পরিস্থিতিতে, বহনযোগ্যতা হারাতে পারে, খারাপভাবে পারফর্ম করতে পারে, প্ল্যাটফর্ম ডেভেলপারদের উপকারী পরিবর্তন করতে বাধা দেয় (এটি আপনাকে ভুলভাবে তৈরি করা অনুমানকে ভঙ্গ করে) কেবলমাত্র বর্তমান প্রয়োগের উপর ভিত্তি করে, ডকগুলি নয়)। আমি মনে করি এটি বেশ খারাপ আচরণ এবং পরামর্শের বেশ খারাপ অংশ।
পলেক

17
@ প্যালেক: "সাধারণত সাবক্লাস অ্যাপ্লিকেশন করার প্রয়োজন হয় না।" - এটা ঠিক ইঙ্গিত। আমি এখনও আনুষ্ঠানিকভাবে ডকুমেন্টেড কার্যকারিতা ইচ্ছাকৃতভাবে ব্যবহার করি। - আমি শুরুতে এই "স্থিতিশীল একক" ব্যবহার করতাম এবং এগুলি একটি… এ ব্যথার কারণ হয়ে দাঁড়ালো - অলস সূচনাটির সমস্যা আছে। বিশেষত যখন উপকরণ পরীক্ষার সাথে ব্যবহার করা হয়। - আমার কাছে এখনও সেই মডেলারিটির জন্য এই সিলেটলেট রয়েছে তবে আমি এগুলি একটি অ্যান্ড্রয়েড.অ্যাপ.অ্যাপ্লিকেশন সাবক্লাসের অনক্রিতে ব্লক করে ইনস্ট্যান্ট করি। - একটি যাদুমন্ত্র মত কাজ করে.
মার্টিন

9
@ মার্টিন আমার এটি পরিষ্কার করে দেওয়া উচিত ছিল: আমার প্রতিক্রিয়া কেবল প্রথম বাক্যটির সাথে সম্পর্কিত। "ডকটি শুনবেন না।" এটি সাধারণত পরামর্শের খুব বিপজ্জনক অংশ। তবে "এটি কেবল একটি ইঙ্গিত - আপনার যদি কোনও কারণ থাকে তবে আপনি এই ক্ষেত্রে ডকটিকে উপেক্ষা করতে পারেন এবং আমি আপনাকে একটি প্রদর্শন করব ..." আমার কাছে একেবারে ঠিক মনে হচ্ছে।
প্লেলে

3
"ব্রডকাস্ট রিসিভারে কোড লেখার সময়, যা কোনও প্রসঙ্গ নয়, তবে এটির অন রিসিভ পদ্ধতিতে একটি প্রসঙ্গ দেওয়া হয়, আপনি কেবল getApplicationContext () কল করতে পারেন Which যার অর্থ এটিও একটি ব্রডকাস্টার রিসিভারে আপনার অ্যাপ্লিকেশনটিতে অ্যাক্সেস পাওয়ার নিশ্চয়তা নেই। " । সুতরাং ব্রডকাস্টরিসিভারে আমার অ্যাপ্লিকেশন শ্রেণিতে অ্যাক্সেসের জন্য আমরা কী করতে পারি?
ডাঃ জ্যাকি

30

তুলনা getApplication()এবং getApplicationContext()

getApplicationএকটি ফেরৎ Applicationবস্তুর যা আপনি যেমন কিছু ডিভাইস পরিস্থিতিতে আপনার গ্লোবাল আবেদন রাষ্ট্র এবং সাড়া পরিচালনা করতে অনুমতি দেবে onLowMemory()এবং onConfigurationChanged()

getApplicationContextগ্লোবাল অ্যাপ্লিকেশন প্রসঙ্গটি ফেরৎ দেয় - অন্যান্য প্রসঙ্গে যেমন পার্থক্য তা হ'ল Android এর দ্বারা আপনার কার্যকলাপ শেষ হয়ে গেলে কোনও ক্রিয়াকলাপের প্রসঙ্গটি ধ্বংস হয়ে যেতে পারে (বা অন্যথায় উপলব্ধ নয়) made আপনার অ্যাপ্লিকেশন অবজেক্টটি উপস্থিত থাকার সময় অ্যাপ্লিকেশন প্রসঙ্গটি সর্বদা উপলভ্য থাকে (যা কোনও নির্দিষ্টের সাথে আবদ্ধ নয় Activity) যাতে আপনি এটি বিজ্ঞপ্তিগুলির মতো জিনিসগুলির জন্য ব্যবহার করতে পারেন যা একটি প্রসঙ্গের প্রয়োজন যা দীর্ঘ সময়ের জন্য উপলব্ধ থাকবে এবং ক্ষণস্থায়ী UI অবজেক্টের থেকে পৃথক থাকবে।

আমার অনুমান যে এটি আপনার কোড কী করছে তার উপর এটি নির্ভর করে যে এগুলি একই হতে পারে বা নাও পারে - যদিও সাধারণ ব্যবহারে, আমি এগুলি আলাদা হওয়ার আশা করব।


19
কিন্তু একটি Application হল একটি Context(এটা তা থেকে উত্তরাধিকারী), এবং রানটাইম এ উভয় পদ্ধতি একই উদাহরণস্বরূপ ফিরে যান। তাহলে পার্থক্য কী?
ম্যাথিয়াস

3
পার্থক্যটি হল সুযোগ। আপনার অ্যাপ্লিকেশন প্রসঙ্গটি একটি ক্রিয়াকলাপের প্রেক্ষাপটের তুলনায় অনেক দীর্ঘ সময় ধরে বৈধ হবে কারণ ক্রিয়াকলাপটি খুব অল্প সময়ের জন্যই ব্যবহৃত হতে পারে, তবে আপনার অ্যাপ্লিকেশনটিতে অনেক ক্রিয়াকলাপ থাকতে পারে। আপনার ক্রিয়াকলাপ প্রবন্ধটি প্রথম ক্রিয়াকলাপ শুরু হওয়ার পরে শুরু হওয়া এবং শেষ ক্রিয়াকলাপে শেষ হওয়ার পরে কমপক্ষে সময়কালের জন্য কার্যকর হবে। এগুলি সমস্ত প্রসংগ, তবে একটি দীর্ঘস্থায়ী এবং পরিবর্তিত হয় না, তবে অন্যরা স্বল্পস্থায়ী এবং বিভিন্ন ক্ষেত্রে বিভিন্ন প্রবন্ধ থাকতে পারে।
রিভেরিকিড

16
আমি মনে করি আপনি আমার প্রশ্নটি ভুলভাবে পড়ছেন। আমি একটি Activityপ্রসঙ্গ এবং প্রসঙ্গে একটি পার্থক্য জিজ্ঞাসা করছি না Application। আমি Application(যা বৈশ্বিক, অনন্য অ্যাপ্লিকেশন প্রসঙ্গ) এবং যে কোনও getApplicationContextরিটার্নের মধ্যে পার্থক্যটি বিবেচনা করছি । আধুনিকটি অ্যানড্রয়েড 1.6 এর আগে আসলে অ-কার্যক্ষম ছিল; এটি সর্বদা ফিরে আসত null
ম্যাথিয়াস

1
@ মাথিয়াস আমার মতে এটি এখনও প্রাসঙ্গিক। প্রসঙ্গটি অ্যান্ড্রয়েড সিস্টেম নিজেই ইনজেকশনের (প্রয়োগ করা) হয়, যখন অ্যাপ্লিকেশনটি উত্তরাধিকার সূত্রে প্রাপ্ত হয় এবং প্রসঙ্গটি প্রসারিত করে। অ্যাপ্লিকেশন ক্লাসটি সহজেই উপহাস করা যায় (যেমন আপনি বলেছেন) তবে এটি কী নিরাপদ বাজি নয় যা এটি দেখায় যে অ্যাপ্লিকেশন শ্রেণি সম্ভবত এটির জন্য কিছু "ম্যাজিক" করেছে (পরীক্ষার প্রকল্পে), সম্ভবত ইনজেক্ট কনটেক্সট উপেক্ষা করে?
অড্রিয়াস

3
আবার আসবেন? আমি দুঃখিত, আমি এখনও দেখতে পাচ্ছি না এটি কীভাবে আমার প্রশ্নের উত্তর দেয়।
ম্যাথিয়াস

30

এটি প্রসঙ্গের মোড়কের সাথে সম্পর্কিত বলে মনে হচ্ছে। প্রাপ্ত বেশিরভাগ ক্লাসগুলি Contextআসলে কContextWrapper , যা মূলত মোড়কের দ্বারা পরিবর্তিত পরিবর্তনগুলির সাথে অন্য একটি প্রসঙ্গে চলে আসে।

প্রসঙ্গটি একটি সাধারণ বিমূর্ততা যা বিদ্রূপ এবং প্রক্সিং সমর্থন করে। যেহেতু অনেকগুলি প্রসঙ্গ যেমন একটি সীমিত-আজীবন অবজেক্টের সাথে আবদ্ধ Activity, তাই ভবিষ্যতের বিজ্ঞপ্তিগুলির জন্য নিবন্ধকরণের উদ্দেশ্যে, দীর্ঘস্থায়ী প্রসঙ্গ পাওয়ার জন্য একটি উপায় থাকা দরকার। এটি দ্বারা অর্জন করা হয় Context.getApplicationContext()। একটি যৌক্তিক বাস্তবায়ন হ'ল বিশ্বব্যাপী Applicationঅবজেক্টটি ফিরিয়ে দেওয়া , তবে কিছুই প্রসঙ্গ প্রয়োগের পরিবর্তে উপযুক্ত জীবনকাল সহ একটি মোড়ক বা প্রক্সি ফিরিয়ে আটকায় না।

ক্রিয়াকলাপ এবং পরিষেবাগুলি নির্দিষ্টভাবে কোনও Applicationসামগ্রীর সাথে সম্পর্কিত। আমি বিশ্বাস করি এর এর কার্যকারিতা হ'ল আপনি ম্যানিফেস্টে একটি কাস্টম ক্লাস তৈরি করেছেন এবং নিবন্ধভুক্ত করতে পারবেন এবং Applicationনিশ্চিত হতে পারেন Activity.getApplication()বা Service.getApplication()সেই নির্দিষ্ট ধরণের নির্দিষ্ট নির্দিষ্ট অবজেক্টটি ফিরিয়ে দিতে পারবেন, যা আপনি আপনার উদ্ভূত Applicationশ্রেণিতে ফেলে দিতে পারেন এবং যা কিছু জন্য ব্যবহার করতে পারবেন কাস্টম উদ্দেশ্য।

অন্য কথায়, getApplication()কোনও Applicationবস্তু ফেরত দেওয়ার নিশ্চয়তা দেওয়া হয় , তবে getApplicationContext()পরিবর্তে প্রক্সি ফেরত দেওয়া মুক্ত।


আপনি যখন বলেন "প্রসঙ্গটি একটি সাধারণ বিমূর্ততা যা বিদ্রূপ এবং প্রক্সিংকে সমর্থন করে" "প্রক্সিং" বলতে কী বোঝায়? আপনি আমাকে কিছু উল্লেখ করতে পারেন? আমি পুরো কনটেক্সট জিনিসটি বেশ সংশ্লেষিত মনে করি।
টিয়াগো

@Tiago এই উত্তরটি সাহায্য করতে পারেন ভালভাবে বুঝতে: stackoverflow.com/questions/10641144/...
সুপার-ইউজার

-13

প্রশ্নের উত্তর দেওয়ার জন্য, getApplication () একটি অ্যাপ্লিকেশন অবজেক্ট ফেরত দেয় এবং getApplicationContext () একটি প্রসঙ্গ বস্তু দেয়। আপনার নিজের পর্যবেক্ষণের উপর ভিত্তি করে, আমি ধরে নেব যে উভয়ের প্রবন্ধটি অভিন্ন (যেমন পর্দার পিছনে অ্যাপ্লিকেশন শ্রেণি উত্তর শ্রেণীর প্রান্তটিকে বেস ক্লাসের প্রসঙ্গ অংশটি বসানোর জন্য ডেকে তোলে বা কিছু সমমানের ক্রিয়া ঘটে)। আপনার যদি কেবল একটি প্রসঙ্গ প্রয়োজন হয় তবে আপনি কোন ফাংশনটিতে কল করবেন তা সত্য নয়।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.