نظرة عامة على إدارة الذاكرة

استخدام بيئة تشغيل Android (ART) وجهاز Dalvik الافتراضي ترقيم الصفحات وربط الذاكرة (mmapping) لإدارة الذاكرة. يعني ذلك أن أي ذاكرة لتطبيق تعديل - سواء من خلال تخصيص الكائنات الجديدة أو لمس الصفحات المحددة — تظل في ذاكرة الوصول العشوائي لا يمكن تقسيمه إلى صفحات. إنّ الطريقة الوحيدة لتحرير ذاكرة من التطبيق هي من خلال التي يحتفظ بها التطبيق، ما يجعل الذاكرة متاحة لجمع القمامة. وذلك باستثناء واحد: أي ملفات دون تعديل، مثل التعليمات البرمجية، خارج ذاكرة الوصول العشوائي (RAM) إذا أراد النظام استخدام تلك الذاكرة في مكان آخر.

توضّح هذه الصفحة آلية Android في إدارة عمليات التطبيقات والذاكرة. التخصيص. لمزيد من المعلومات حول كيفية إدارة الذاكرة بكفاءة أكبر في تطبيقك، واطّلِع على إدارة ذاكرة تطبيقك

جمع القمامة

بيئة ذاكرة مُدارة، مثل جهاز ART أو Dalvik الافتراضي على تتبع كل عملية تخصيص للذاكرة. بعد تحديد أي جزء من الذاكرة لم يعد يستخدمه البرنامج، ويعيد نقلها إلى كومة الذاكرة المؤقتة، بدون تدخّل المبرمج. آلية استرداد الذاكرة غير المستخدَمة داخل بيئة ذاكرة مُدارة تُعرف باسم جمع البيانات غير المرغوب فيها. ينطوي جمع القمامة على هدفين: العثور على عناصر بيانات في برنامج لا يمكن الوصول إليها في المستقبل أو استرداد الموارد التي تستخدمها هذه الكائنات.

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

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

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

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

للحصول على مزيد من المعلومات العامة عن جمع البيانات غير المرغوب فيها، يمكنك الاطّلاع على جمع القمامة:

مشاركة الذكريات

من أجل ملاءمة كل ما يحتاج إليه في ذاكرة الوصول العشوائي، يحاول Android مشاركة صفحات ذاكرة الوصول العشوائي (RAM) على مستوى العمليات. أُنشأها جون هنتر، الذي كان متخصصًا يمكنك القيام بذلك بالطرق التالية:

  • تنشأ كل عملية تطبيق من عملية حالية تسمى Zygote. تبدأ عملية Zygote عند تشغيل النظام وتحميله بشكل شائع رمز إطار العمل والموارد (مثل مواضيع الأنشطة). لبدء عملية جديدة للتطبيق، يتشعّب النظام لعملية Zygote ثم تحميل رمز التطبيق وتشغيله في العملية الجديدة. يسمح هذا الأسلوب بمعظم صفحات ذاكرة الوصول العشوائي (RAM) المخصصة رمز إطار العمل والموارد التي ستتم مشاركتها في جميع عمليات التطبيق.
  • يتم إشراك معظم البيانات الثابتة في عملية. يتيح هذا الأسلوب مشاركة البيانات. بين العمليات، ويسمح أيضًا بتقسيمها عند الحاجة. تتضمن أمثلة البيانات الثابتة ما يلي: رمز Dalvik (من خلال وضعه في .odex مرتبط مسبقًا) ملف للتأليف المباشر)، وموارد التطبيق (من خلال تصميم جدول الموارد ليكون هيكلاً التي يمكن إدخالها ومن خلال محاذاة الرمز لإدخال APK)، ومشروع تقليدي عناصر مثل الرموز الأصلية في ملفات .so.
  • يتشارك Android في العديد من الأماكن نفس الطابع الديناميكي. ذاكرة الوصول العشوائي (RAM) عبر العمليات باستخدام المساحات المخصصة مناطق الذاكرة المشتركة (إما مع ashmem أو gralloc). على سبيل المثال، تستخدم أسطح النوافذ مشتركة والذاكرة بين التطبيق ومكوّن الشاشة تستخدم المخازن المؤقتة للمؤشر الذاكرة المشتركة بين وموفر المحتوى وعميله.

نظرًا للاستخدام المكثّف للذاكرة المشتركة، أصبح تحديد مساحة الذاكرة التي يستخدمها تطبيقك الرعاية. أساليب لتحديد مستوى تعريف تطبيقك استخدام الذاكرة في التحقيق في استخدام ذاكرة الوصول العشوائي (RAM)

تخصيص ذاكرة التطبيق واستردادها

تقتصر كومة دالفيك على نطاق ذاكرة افتراضية واحد لكل عملية تطبيق. هذا يحدد حجم الذاكرة المنطقية، والذي يمكن أن يزداد عند ولكن فقط إلى الحدّ الذي يحدّده النظام لكل تطبيق.

ولا يتطابق الحجم المنطقي للذاكرة مقدار الذاكرة الفعلية التي تستخدمها كومة الذاكرة المؤقتة. عند فحص كومة الذاكرة المؤقتة في التطبيق، يحتسب Android قيمة تسمى حجم المجموعة التناسبي (PSS)، يراعي كلاً من الصفحات غير النظيفة والنظيفة التي تتم مشاركتها مع عمليات أخرى - ولكن فقط في يتناسب مع عدد التطبيقات التي تشارك ذاكرة الوصول العشوائي هذه. هذا الإجمالي (PSS) هو ما يحدده النظام المستخدم كبصمة للذاكرة. لمزيد من المعلومات حول PSS، يُرجى الاطّلاع على التحقيق في استخدام ذاكرة الوصول العشوائي الدليل.

لا تضغط كومة دالفيك على المفتاح المنطقي أي حجم لك، ما يعني أنّ نظام Android إلغاء تجزئة كومة الذاكرة لإغلاق مساحة جهاز Android يمكن فقط تقليص حجم الذاكرة المنطقية عند مساحة غير مُستخدَمة في نهاية الذاكرة ومع ذلك، لا يزال بإمكان النظام تقليل الذاكرة الفعلية التي تستخدمها كومة الذاكرة المؤقتة. بعد جمع القمامة، قامت دالفيك يسير في كومة الذاكرة وعثر على الصفحات غير المستخدمة، ثم يعود تلك الصفحات إلى النواة باستخدام الجنون. لذلك، تم إقران مخصصات وصفقات كبيرة إلى استرداد جميع البيانات (أو جميعها تقريبًا) الذاكرة الفعلية المستخدمة. ومع ذلك، يمكن أن يكون استرداد الذاكرة من خلال تخصيصات صغيرة أمرًا أقل كفاءة لأن الصفحة استخدمت أن تتم مشاركة حصة صغيرة مع شيء آخر لم يتم تحريره بعد.

حظر استخدام ذاكرة التطبيق

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

في بعض الحالات، قد ترغب في الاستعلام عن لتحديد مقدار مساحة كومة الذاكرة المؤقتة المتاحة على الجهاز الحالي - على سبيل المثال، لتحديد مقدار البيانات الذي يمكن الاحتفاظ به بشكل آمن في ذاكرة التخزين المؤقت. يمكنك الاستعلام من النظام عن هذا الرقم من خلال استدعاء getMemoryClass() ويكون ناتج هذه الطريقة عددًا صحيحًا يشير إلى عدد وحدة ميغابايت متاحة لكومة الذاكرة المؤقتة لتطبيقك.

تبديل التطبيقات

عندما يبدّل المستخدمون بين التطبيقات، يحتفظ Android بالتطبيقات التي ليست في المقدّمة - أي لا تكون مرئية للمستخدم أو تشغّل خدمة تعمل في المقدّمة مثل تشغيل الموسيقى في ذاكرة التخزين المؤقت. على سبيل المثال، عندما يشغّل المستخدم تطبيقًا لأول مرة، إنشاء عملية لها؛ ولكن عندما يفكر مغادرة التطبيق، فإن هذه العملية لا تتوقف. ويحتفظ النظام بالعملية في ذاكرة التخزين المؤقت. في حال حذف يعود المستخدم إلى التطبيق لاحقًا، يعيد النظام استخدام العملية، وبالتالي مما يجعل تبديل التطبيق أسرع.

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

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

لمزيد من المعلومات حول كيفية تخزين العمليات مؤقتًا أثناء لا يعمل في المقدّمة وكيف يحدّد Android التطبيقات القتل، يمكنك رؤية العمليات وسلاسل المحادثات الدليل.

اختبار إجهاد الذاكرة

رغم أنّ مشاكل إجهاد الذاكرة أقل شيوعًا على الأجهزة المتطورة، إلا أنّها قد تسبب مشاكل للمستخدمين الذين يستخدمون الأجهزة ذات ذاكرة الوصول العشوائي المنخفضة، مثل الأجهزة التي تعمل بنظام التشغيل Android (إصدار Go). من المهم أن تحاول إعادة إنتاج هذه البيئة التي تعاني من إجهاد الذاكرة كي تتمكن من كتابة اختبارات قياس حالة التطبيق للتحقق من التطبيق السلوك وتحسين تجربة المستخدمين على الأجهزة ذات الذاكرة المنخفضة.

اختبار التطبيق المجهد

اختبار التطبيق المكثف (stressapptest) هو اختبار لواجهة الذاكرة يساعد في إنشاء مواقف واقعية ومليئة بالحِمل لاختبار وحدات ذاكرة متنوعة والقيود المفروضة على الأجهزة في تطبيقك. من خلال القدرة على تحديد قيود الوقت والذاكرة، يسمح لك بكتابة أدوات للتحقق من الأحداث الواقعية للمواقف التي تتميز بذاكرة كبيرة. على سبيل المثال، استخدم مجموعة الأوامر التالية لإرسال المكتبة الثابتة في نظام ملفات البيانات الخاص بك، اجعله قابلاً للتنفيذ، وأجرِ اختبار إجهاد لمدة 20 ثانية بحجم 990 ميغابايت:
    adb push stressapptest /data/local/tmp/
    adb shell chmod 777 /data/local/tmp/stressapptest
    adb shell /data/local/tmp/stressapptest -s 20 -M 990

  

يمكنك الاطّلاع على stressapptest. وثائق لمزيد من المعلومات حول تثبيت الأداة، والوسيطات الشائعة، ومعالجة الأخطاء المعلومات.

ملاحظات حول اختبار الإجهاد

يمكن استخدام أدوات مثل stressapptest لطلب عمليات تخصيص للذاكرة أكبر من حرية الاختيار. المتوفرة. ويمكن أن يؤدي هذا النوع من الطلبات إلى ظهور تنبيهات متنوعة، والتي يجب أن تكون على دراية بها من جانب التطوير. تشمل ثلاثة تنبيهات رئيسية يمكن إصدارها بسبب انخفاض مدى توفّر الذاكرة ما يلي:
  • SIGABRT: إنه عطل خطير أصلي في عمليتك بسبب طلب تخصيصات أكبر من الذاكرة الخالية، في حين أن النظام تحت ضغط الذاكرة بالفعل.
  • SIGQUIT: ينشئ تفريغ الذاكرة الأساسي وينهي العملية عندما يكتشفه اختبار قياس حالة التطبيق.
  • TRIM_MEMORY_EVENTS: تتوفّر عمليات معاودة الاتصال هذه على Android 4.1 (المستوى 16 من واجهة برمجة التطبيقات) والإصدارات الأحدث، وتوفر معلومات تفصيلية من أجل عمل تنبيهات الذاكرة.