سؤال

في الكود الخاص بي ، أستخدم كائن Singleton كنقطة مركزية في تطبيقي لتحميل وتخزين الصور التي يحتاجها التطبيق بشكل متكرر ، لذلك لا يتعين عليّ إجراء تخصيص ذاكرة كثيفة الموارد في كل مرة أقوم فيها بتحميل صورة.

ولكن هناك أوقات أثناء تنفيذ تطبيقي حيث يصبح استخدام الذاكرة مكثفًا وأرغب في إصدار بيانات الصورة المخزنة مؤقتًا. حاليًا ، أقوم فقط بإصدار مثيلات Uiimage من Singleton عندما أحصل على تحذير من الذاكرة.

ومع ذلك ، أفضل أن أكون قادرًا على إطلاق كائن Singleton بأكمله. هل هذا ممكن؟ إذا كان الأمر كذلك ، كيف؟

هل كانت مفيدة؟

المحلول

بالطبع هو كذلك. على الرغم من أنه من المحتمل أن يكون استخدام ذاكرة هذا الكائن ضئيلًا مقارنة بالصور.

حسب طبيعة المفرد ، يجب أن يكون لديك ملحق به ، حيث ستنشئه إذا لم يكن موجودًا حاليًا:

+ (MySingletonClass*) mySingleton
{
    if ( mySingleton == nil )
    {
        mySingleton = [[MySingletonClass alloc] init];
    }

    return mySingleton;
}

تحتاج فقط إلى إضافة آخر تتصل به عندما تريد تدميره:

+ (void) destroyMySingleton
{
    [mySingleton release];
    mySingleton = nil;
}

إذا واصلت الإشارات إليها في مكان آخر ، فستواجه مشكلة ؛ لا تفعل ذلك. إذا قمت بالوصول من سلاسل خيوط متعددة ، فستحتاج إلى مزامنة. خلاف ذلك ، إنه أمر واضح ومباشر - سيتم إعادة إنشاء getter عندما تحتاجه بعد ذلك.

نصائح أخرى

فيما يلي مثال على ملحق Singleton للرمز المفتوح الذي أستخدمه.

  // Eric Wing. Singleton accessor.  This is how you should ALWAYS get
  // a reference to the sound controller.  Never init your own.
  + (OpenALSoundController*) sharedController
 {
  static OpenALSoundController* shared_sound_controller;
  @synchronized(self)
  {
   if (nil == shared_sound_controller)
    {
     shared_sound_controller = [[OpenALSoundController alloc] init];
    }
  }      
  return shared_sound_controller;
 }

يأخذ Openal بعض الوقت للتحميل ، لذا فإن الاحتفاظ بمثلة واحدة حولها هو بالضبط ما أحتاجه. مع وجود أكثر من موضوع واحد في اللعب (وليس وضعي حاليًا ، لكنني أريد نقل الكود الخاص بي إلى المواقف التي يكون فيها هذا هو الحال) وضعت قفلًا self. @synchronized(self) يفعل ذلك بالضبط.

الآن قمت بتخصيص الذاكرة لذلك أنا مسؤول عن إطلاقها. يمكنني الاتصال [shared_sound_controller autorelease] في ال +sharedController طريقة الملحقات ولكن هذا قد يصدر وحدة التحكم في وقت مبكر ، خاصة عندما يكون لدي أكثر من مؤشر ترابط واحد وأتصل بالملحق لأول مرة في مؤشر ترابط ليس الخيط الرئيسي.

أي كائن تقوم بإنشائه يمكنك إطلاقه في أي وقت. (على افتراض أنك تنشئها وتعيين خصائصها.)

self.myObject = [[myObjectClass alloc] init];
    // do something with the object
   [self.myObject release];       // anytime that you are not using the object

self.myObject = nil; // will also work if you've set the @property (retain, nonatomic)
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top