الأداء في تطوير التطبيقات المحمولة: ما هو، ما هي المقاييس وكيفية التحسين

المؤلف: IT Sectr نُشر: 2026-03-25 وقت القراءة: 12 دق

التطبيق البطيء هو السبب الرئيسي الذي يدفع المستخدمين لحذف البرامج. أجزاء من الثانية من التأخير عند بدء التشغيل أو التمرير في القائمة تقلل معدل الاحتفاظ بالمستخدمين بنسبة عشرات في المئة. الأداء (performance) ليس فقط السرعة، بل أيضاً الاستقرار: غياب ANR والأعطال وتسريبات الذاكرة. في هذه المقالة سنغطي جميع جوانب الأداء: من إدارة الذاكرة (GC, ARC) إلى التنميط باستخدام الأدوات. للمزيد — في الدليل الرسمي لأداء Android.

أهم النقاط

  • ANR والأعطال — أعدى أعداء تجربة المستخدم؛ يتم منعها باستخدام خيوط المعالجة الخلفية
  • تسريب الذاكرة ودورة الاحتفاظ يؤديان إلى أعطال OOM؛ يتم حلها باستخدام المراجع الضعيفة والأدوات المساعدة
  • GC (أندرويد) و ARC (آي أو إس) — نماذج إدارة الذاكرة؛ فهم عملها أمر بالغ الأهمية
  • التنميط (Instruments, Android Profiler, LeakCanary) — مرحلة تطوير إلزامية
  • بدء التشغيل البارد — أهم مقياس للإطلاق؛ تحسين Application.onCreate والتهيئة البطيئة
  • حجم التطبيق — استخدام App Bundle و R8 و VectorDrawable و WebP لتقليل الحجم

لماذا التطبيق بطيء؟

يرتبط أداء التطبيق ارتباطاً مباشراً بالتباطؤ (jank) — تأخير ملحوظ بين إجراء المستخدم واستجابة الواجهة. الأسباب الرئيسية: حظر الخيط الرئيسي (عمليات ثقيلة على خيط واجهة المستخدم)، إعادة رسم التخطيط المتكررة (overdraw)، تسريبات الذاكرة (GC متكرر)، خوارزميات غير مثلى (O(n²) على بيانات كبيرة). معدل الإطارات (FPS) — عدد الإطارات في الثانية. لتجربة مريحة تحتاج إلى 60 إطاراً في الثانية مستقرة (أندرويد) أو 120 إطاراً في الثانية (iPhone Pro, iPad Pro). VSync — مزامنة الرسم مع معدل تحديث الشاشة.

يحدث التباطؤ عندما يتجاوز رسم إطار واحد 16.6 مللي ثانية (لـ 60 FPS) أو 8.3 مللي ثانية (لـ 120 FPS). يُظهر تنميط GPU (Profile GPU Rendering على أندرويد، Core Animation على آي أو إس) مراحل الرسم التي تستغرق معظم الوقت. المراحل الرئيسية: Layout (ترتيب العناصر)، Draw (الرسم)، Display (النقل إلى مخزن الإطارات). المشكلة الأكثر شيوعاً هي تضخم التخطيط في XML، خاصة عند استخدام ConstraintLayout المتداخلة المعقدة.

الوقت حتى التفاعل (TTI) — الوقت الذي يستغرقه التطبيق ليصبح جاهزاً تماماً للتفاعل. يشمل TTI بدء التشغيل البارد وتحميل البيانات وتهيئة المكتبات. توصي Google بأن يكون TTI أقل من 5 ثوانٍ، وتوصي Apple بأقل من ثانيتين للشاشات الرئيسية. التحميل البطيء (Lazy Loading) — تقنية تحميل مؤجل للمحتوى والمكتبات، وهي ضرورية لتحسين TTI. في IT Sectr نستخدم التهيئة البطيئة افتراضياً في جميع المشاريع.

ANR والأعطال

ANR والأعطال — أعدى أعداء أداء التطبيق المحمول. ANR (Application Not Responding) — مربع حوار يظهر على أندرويد إذا كان الخيط الرئيسي محظوراً لأكثر من 5 ثوانٍ. الأسباب: طلبات شبكة متزامنة على خيط واجهة المستخدم، العمل مع قاعدة بيانات بدون coroutines، فك تشفير صورة كبيرة بدون downsampling، deadlock على الخيط الرئيسي. مكدس استدعاءات ANR يُحفظ في /data/anr/traces.txt ويسمح بتحديد موقع الحظر بدقة.

العطل — إنهاء غير متوقع للتطبيق. على أندرويد — Exception (Java/Kotlin) أو Signal (كود أصلي). على آي أو إس — NSException أو إشارة (EXC_BAD_ACCESS — الوصول إلى ذاكرة محررة). أدوات الإبلاغ عن الأعطال: Firebase Crashlytics, Sentry, BugSnag. تجمع stacktrace وبيانات الجهاز وخطوات إعادة الإنتاج. Stack Overflow — تجاوز مكدس الاستدعاءات بسبب التكرار اللانهائي. OutOfMemoryError — عندما يكون الكومة ممتلئة.

StrictMode — أداة أندرويد لاكتشاف انتهاكات أمان الخيوط. تسمح بتعيين قواعد: ThreadPolicy (منع القرص/الشبكة على الخيط الرئيسي)، VmPolicy (كشف تسريبات Activity و SQLite و CloseGuard). يوصى بتفعيل StrictMode فقط في بنية التصحيح — في الإصدار النهائي لا يجب أن يعمل. على آي أو إس المكافئ هو Main Thread Checker (Xcode)، الذي يكشف تلقائياً استدعاءات UIKit خارج الخيط الرئيسي.

إدارة الذاكرة (GC, ARC, Retain Cycle)

تسريب الذاكرة

تسريب الذاكرة — حالة يبقى فيها الكائن في الذاكرة على الرغم من أن التطبيق لم يعد يستخدمه. هذا يقلل أداء التطبيق مباشرة. على أندرويد، GC (Garbage Collection) لا يمكنه جمع كائن إذا كان هناك مرجع قوي إليه. الأسباب النموذجية: مراجع ثابتة إلى Activity، استدعاءات/مراقبين غير ملغاة، فئات داخلية بمرجع ضمني إلى الفئة الخارجية، Handler برسائل غير منقاة. LeakCanary — مكتبة للكشف التلقائي عن التسريبات.

دورة الاحتفاظ (Retain Cycle)

ARC (Automatic Reference Counting) — نموذج إدارة الذاكرة في آي أو إس. كل كائن له عداد مراجع (retain count). عند وصول العداد إلى الصفر، يتم تحرير الذاكرة. تحدث دورة الاحتفاظ عندما يحتفظ كائنان بمراجع قوية لبعضهما البعض (A → B و B → A). لن يقوم ARC أبداً بتصفير العدادات. الحل: مراجع ضعيفة (weak) أو بدون مالك (unowned). Weak تلغى تلقائياً (تصبح nil) عند تحرير الكائن. Unowned لا تُلغى لكنها تضمن أن الكائن حي.

GC ضد ARC

GC (Garbage Collection) يعمل على أندرويد (Java/Kotlin). GC يوقف التنفيذ دورياً (إيقاف Stop-the-World) للبحث عن الكائنات غير القابلة للوصول وتحريرها. مشغل GC: عند امتلاء الكومة بنسبة معينة. ARC يعمل على آي أو إس (Swift/Objective-C) وليس لديه إيقافات — يتم تحديث العدادات ذرياً مع كل تعيين. ARC أكثر قابلية للتنبؤ لكنه قد يراكم عمليات retain/release زائدة عند تردد تعيين عالٍ.

المرجع الضعيف والمرجع القوي — نوع المرجع يحدد ما إذا كان GC/ARC يمكنه تحرير الكائن. المرجع القوي — لن يتم جمع الكائن طالما هذا المرجع موجود. المرجع الضعيف — GC/ARC يمكنه جمع الكائن؛ المرجع الضعيف يصبح nil (في Swift/Java WeakReference). Unowned Reference (Swift) — لا تُلغى عند التحرير؛ الوصول إليها بعد موت الكائن يسبب عطلاً. على أندرويد يُستخدم java.lang.ref.WeakReference للمراجع الضعيفة.

مثال على كشف تسريب على أندرويد باستخدام LeakCanary:

kotlin
// Утечка: анонимный класс держит ссылку на Activity
class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        val handler = object : Handler(Looper.getMainLooper()) {
            override fun handleMessage(msg: Message) {
                // Используем `this@MainActivity`, сохраняя ссылку на Activity
                Log.d("TAG", "Handler received message")
            }
        }
        handler.sendEmptyMessageDelayed(0, 60000)
    }
}

// Исправление: статический Handler + WeakReference
class SafeHandler(activity: MainActivity) : Handler() {
    private val weakActivity =
        WeakReference(activity)

    override fun handleMessage(msg: Message) {
        weakActivity.get() ?: return
        Log.d("TAG", "Handler received message")
    }
}

التنميط (Instruments, Android Profiler)

التنميط — عملية قياس أداء التطبيق: وحدة المعالجة المركزية والذاكرة والشبكة واستهلاك الطاقة. بدون تنميط، التحسين الأعمى غير مفيد — لن تعرف أي جزء من الكود يبطئ التطبيق حقاً.

الأداة المنصة تقيس متى تستخدم
Instruments (Time Profiler)iOSCPU، استدعاءات الدوال، وقت التنفيذتحسين الخوارزميات، البحث عن الاختناقات
Instruments (Allocations)iOSالذاكرة، عدد الكائنات، retain countsالبحث عن التسريبات واستهلاك الذاكرة الزائد
Instruments (Leaks)iOSدورات الاحتفاظ، تسريبات الذاكرةالفحص المنتظم قبل الإصدار
Android Profiler (CPU)Androidاستخدام CPU، نشاط الخيوط، tracesالبحث عن حظر الخيط الرئيسي
Android Profiler (Memory)AndroidHeap dump، تتبع التخصيصالبحث عن التسريبات، تحليل الكائنات
Android Profiler (Network)Androidحركة المرور، السرعة، توقيت الطلباتتحسين استدعاءات الشبكة
LeakCanaryAndroidكشف تلقائي لتسريبات الذاكرةفي جميع مراحل التطوير
StrictModeAndroidالقرص/الشبكة على الخيط الرئيسي، التسريباتبنية التصحيح
Traceview / SystraceAndroidتتبع الدوال، أحداث النظامتحليل عميق للتأخير

Instruments (Xcode) — أقوى أداة لـ iOS. يُظهر Time Profiler أي الدوال تستهلك معظم CPU. يتتبع Allocations إنشاء وتحرير الكائنات. يجد Leaks تلقائياً دورات الاحتفاظ. خطوات التنميط: (1) تشغيل Instruments؛ (2) اختيار قالب (Time Profiler لوحدة المعالجة المركزية)؛ (3) تنفيذ السيناريو المشكل؛ (4) تحليل مكدس الاستدعاءات — أوسع عمود هو الدالة الأكثر استهلاكاً.

Android Profiler مدمج في Android Studio (View → Tool Windows → Profiler). يُظهر CPU Profiler حمل كل خيط. Memory Profiler — heap dump وتتبع التخصيص. Network Profiler — جميع طلبات HTTP مع التوقيتات. Energy Profiler — استهلاك الطاقة: WakeLock, Location, Network. للتتبع المفصل يُستخدم Systrace (Android 10+) أو Perfetto — تتبع النظام بدقة ميكروثانية.

بدء تشغيل التطبيق (بدء بارد/دافئ/ساخن)

بدء تشغيل التطبيق — أحد المؤشرات الرئيسية للأداء. ينقسم إلى ثلاثة أنواع: بدء بارد — يبدأ التطبيق من الصفر: يتم إنشاء العملية، Application.onCreate (أندرويد) / AppDelegate.applicationDidFinishLaunching (آي أو إس)، تحميل الفئات، تهيئة المكتبات. بدء دافئ — العملية موجودة لكن Activity/ViewController مُدمر (مثلاً عند تدوير الشاشة أو العودة من الذاكرة). بدء ساخن — Activity/ViewController في الذاكرة، التطبيق يظهر ببساطة (التبديل من تطبيق آخر).

بدء التشغيل البارد هو أهم مقياس. على أندرويد يشمل: (1) إطلاق Activity — تحميل XML، تهيئة View؛ (2) أول إطار — الوقت حتى أول رسم. توصي Google بأن يكون إطلاق Activity < 200 مللي ثانية، أول إطار < 500 مللي ثانية، TTI < 5 ثوانٍ. تحسين بدء التشغيل البارد: تقليل Application.onCreate (coroutines للتهيئة البطيئة)، استخدام SplashScreen API (Android 12+)، تأجيل تهيئة المكتبات (WorkManager, DI)، إزالة ContentProviders غير الضرورية.

على آي أو إس، يشمل بدء التشغيل البارد: تحميل الملف الثنائي Mach-O، dyld (الرابط الديناميكي)، تهيئة بيئة تشغيل Objective-C، مفوض التطبيق، أول وحدة تحكم. Chrome Custom Tabs (أندرويد) و Universal Links (آي أو إس) — تقنيات لفتح المحتوى الخارجي بسرعة في التطبيق بدون بدء تشغيل بارد كامل. يوصى باختبار بدء التشغيل البارد على أجهزة حقيقية من الفئة المتوسطة.

تحسين الحجم

حجم التطبيق — عامل أداء للتثبيت والتحديثات. يؤثر على معدل التحويل: كل 10 ميغابايت تقلل التحويل بنسبة 1%. توصي Google Play بحجم APK أقل من 150 ميغابايت؛ App Store — أقل من 200 ميغابايت (الشبكات الخلوية — 100 ميغابايت). طرق التحسين الرئيسية: ضغط الصور (WebP بدلاً من PNG يوفر 25-35%)، التوجيه (VectorDrawable على أندرويد، SF Symbols على آي أو إس)، إزالة الكود غير المستخدم (R8/ProGuard)، إزالة الموارد غير المستخدمة (lint → unused resources).

App Bundle (أندرويد) — تنسيق نشر حيث يُنشئ Google Play APK محسناً لكل جهاز. يقلل App Bundle حجم التنزيل بنسبة 20-40%. Dynamic Delivery — وحدات تُحمّل عند الطلب (on-demand feature modules). على آي أو إس المكافئ هو On-Demand Resources (ODR): موارد تُحمّل بعد بدء التشغيل الأول (مستويات اللعبة، فيديوهات).

التحميل البطيء — تقنية لا تُحمّل فيها الوحدات والمكتبات عند بدء التشغيل بل تُحمّل حسب الحاجة. Split APK (أندرويد) و App Slicing (آي أو إس) — تقسيم التطبيق إلى فتحات معمارية: arm64-v8a, x86_64. تحسين حجم التطبيق — عملية مستمرة: حلل تكوين APK (Analyze APK في Android Studio)، أزل الأيقونات المكررة، استخدم SVG بدلاً من عدة كثافات PNG. في IT Sectr نضمن فحص حجم البناء في CI/CD لكل MR.

الأسئلة الشائعة

ما هو ANR وكيف نتجنبه؟

ANR (Application Not Responding) — مربع حوار يظهر على أندرويد إذا كان الخيط الرئيسي محظوراً لأكثر من 5 ثوانٍ. لتجنب ANR، انقل جميع العمليات الثقيلة (الشبكة، قاعدة البيانات، معالجة الملفات) إلى خيوط خلفية. المكافئ على آي أو إس — frozen UI، عندما يتوقف التطبيق عن الاستجابة للمسات.

ما هو تسريب الذاكرة ودورة الاحتفاظ؟

تسريب الذاكرة — عندما لا يمكن تحرير كائن بسبب وجود مراجع إليه. دورة الاحتفاظ — حالة في iOS/Objective-C حيث يشير كائنان إلى بعضهما البعض (A → B → A) ولا يمكن لـ ARC تحرير أي منهما. الحل: مراجع weak/unowned وتنظيف الاستدعاءات في الوقت المناسب.

ما الأدوات المستخدمة للتنميط؟

لـ iOS: Instruments (Time Profiler, Allocations, Leaks). لـ Android: Android Profiler (CPU, Memory, Network)، LeakCanary (تسريبات الذاكرة)، StrictMode (انتهاكات الخيوط). يوصى بدمج التنميط خلال مرحلة التطوير والتكامل.

ما الفرق بين بدء التشغيل البارد والدافئ والساخن؟

بدء بارد — يبدأ التطبيق من الصفر: تُنشأ العملية، تُحمّل الفئات، يُنفّذ Application.onCreate. بدء دافئ — العملية موجودة لكن Activity/ViewController يُعاد إنشاؤها. بدء ساخن — Activity/ViewController موجودة في الذاكرة، تُعرض ببساطة. بدء التشغيل البارد هو الأبطأ (1-5 ثوانٍ) وهو مهم لتجربة المستخدم.

كيف نقلل حجم التطبيق المحمول؟

الطرق الرئيسية: إزالة الموارد والكود غير المستخدمين (استخدم R8/ProGuard)، توجيه الصور (VectorDrawable, SF Symbols)، ضغط PNG/WebP (أندرويد)، استخدام App Bundle بدلاً من APK، إزالة المكتبات غير الضرورية، استخدام التحميل البطيء للوحدات. تحسين الحجم يمكن أن يقلل APK بنسبة 40-60%.

الملخص

  • ANR والأعطال — مشاكل الاستقرار الرئيسية؛ تُحل بالخيوط الخلفية ومبلّغي الأعطال
  • تسريب الذاكرة ودورة الاحتفاظ — الأسباب الرئيسية لـ OOM؛ تُحل بالمراجع الضعيفة و LeakCanary
  • GC (إيقافات Stop-the-World) ضد ARC (بدون إيقافات لكن مع دورات احتفاظ) — نماذج ذاكرة مختلفة
  • التنميط — مرحلة إلزامية: Instruments (iOS)، Android Profiler، LeakCanary، StrictMode
  • بدء التشغيل البارد — مقياس رئيسي؛ تحسين Application.onCreate والتهيئة البطيئة
  • App Bundle و WebP/VectorDrawable — الأدوات الرئيسية لتقليل الحجم بنسبة 20-60%
  • الأداء عملية مستمرة، وليس نشاطاً لمرة واحدة؛ أدخل المقاييس في CI/CD

سنقوم بتطوير تطبيق جوال جاهز

تقدم IT Sectr تطبيقات iOS وAndroid للشركات الناشئة والشركات منذ عام 2017. سوف نقدم لك النصح ونقترح أفضل حل.

مناقشة المشروع