انتقل إلى المحتوى الرئيسي

الوحدة 6 — التقطيع الدلالي: U-Net وDeepLab

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

المُشفِّر-فاكّ الشفرة مع وصلات التخطّي

المعمارية الأساسية للتقطيع الدلالي هي المُشفِّر-فاكّ الشفرة (encoder-decoder). المُشفِّر يُقلّص الدقّة تدريجيًا مع زيادة العمق (كـCNN تقليدية للتصنيف)، ويلتقط سمات دلالية غنيّة. فاكّ الشفرة يعكس هذا: يرفع الدقّة تدريجيًا حتى تعود إلى دقّة الدخل، وينتج قناعًا يُصنّف كلّ بكسل.

المشكلة الأولى: المُشفِّر يُفقد المعلومات المكانية الدقيقة أثناء التقليص. حين نُعيد الرفع، لا نستطيع استعادة حواف حادّة بين الطريق والرصيف.

طرح U-Net (Ronneberger et al.، 2015، للتصوير الطبّي أصلًا) الحلّ العبقري: وصلات التخطّي (skip connections). كلّ طبقة في المُشفِّر تُوصَل مباشرةً بالطبقة المقابلة في فاكّ الشفرة، ما يُتيح لفاكّ الشفرة أن يستعيد التفاصيل المكانية الدقيقة التي فقدها المُشفِّر. الاسم «U-Net» جاء من شكل المعمارية عند رسمها: حرف U، مع الوصلات الأفقية التي تعبر بين الجانبين.

معمارية U-Net بالتفصيل

كلّ خطوة في المُشفِّر تتكوّن من ثلاث عمليّات:

  1. التفافيتان 3×3 مع تنشيط ReLU لاستخراج السمات
  2. تجميع أقصى (max pooling) 2×2 لتنصيف الدقّة
  3. تضعيف عدد القنوات في الخطوة التالية

وفاكّ الشفرة يعكس ذلك:

  1. تفكيك الالتفاف (deconvolution) أو رفع الدقّة (upsampling) لمضاعفة الدقّة
  2. تسلسل مع خريطة سمات المُشفِّر المقابلة عبر وصلة التخطّي
  3. التفافيتان 3×3 مع ReLU لدمج المعلومات

الطبقة الأخيرة التفافية 1×1 تُقلّص القنوات إلى عدد الأصناف، ثم softmax على البكسلات ينتج قناعًا للأصناف.

Atrous Convolution وDeepLab

U-Net يعمل بالتقليص ثم الرفع، وهو ما يُفقد دقّة تدريجيًا. عائلة DeepLab (Chen et al.، Google، من v1 إلى v3+) اقترحت مقاربة مختلفة: الاحتفاظ بدقّة عالية طوال الشبكة، مع توسيع الحقل الاستقبالي بطريقة أخرى.

الأداة الأساسية هي الالتفاف الموسّع (atrous convolution، أو dilated convolution). التفاف 3×3 عادي ينظر إلى 9 بكسلات متجاورة. التفاف مُوسَّع بمعامل r=2r = 2 ينظر إلى 9 بكسلات لكن بينها فراغ: بكسل، تخطّي، بكسل، تخطّي. النتيجة حقل استقبالي أوسع بدون زيادة عدد الوسائط.

y[i]=kx[i+rk]w[k]y[i] = \sum_{k} x[i + r \cdot k] \cdot w[k]

بجمع معدّلات rr مختلفة بالتوازي في وحدة Atrous Spatial Pyramid Pooling (ASPP)، تلتقط DeepLab أنماطًا على مقاييس متعدّدة في نفس الطبقة. هذا مفيد للتقطيع الحضري حيث تتعايش الأجسام الصغيرة (لوحة إشارة) مع الكبيرة (طريق واسع).

DeepLabv3+ أضاف فاكّ شفرة خفيفًا لصقل الحواف، ويُعدّ اليوم مرجعًا صلبًا للتقطيع الدلالي على البيانات الحضرية مثل Cityscapes.

خسارة Dice وخسارة IoU

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

  • بكسلات «سماء»: 30%
  • بكسلات «طريق»: 40%
  • بكسلات «مبانٍ»: 25%
  • بكسلات «مُشاة»: أقلّ من 1%

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

خسارة Dice تعالج ذلك مباشرة. تُقاس بين قناع مُتنبَّأ به PP وقناع حقيقي GG:

LDice=12PGP+G\mathcal{L}_{\text{Dice}} = 1 - \frac{2 |P \cap G|}{|P| + |G|}

فيها البسط والمقام يتناسبان مع حجم القناع، فتصير الخسارة مستقلّة عن حجم الصنف. صنف صغير جدًّا يُنتج تدرّجًا قويًّا حين نُغفله، بعكس إنتروبيا متقاطعة.

خسارة IoU (تسمّى أيضًا Jaccard) شبيهة:

LIoU=1PGPG\mathcal{L}_{\text{IoU}} = 1 - \frac{|P \cap G|}{|P \cup G|}

كلاهما فعّال. الممارسة الشائعة هي مزج إنتروبيا متقاطعة مع Dice: L=0,5CE+0,5Dice\mathcal{L} = 0{,}5 \cdot \text{CE} + 0{,}5 \cdot \text{Dice}، ما يجمع بين استقرار CE وحساسيّة Dice للأقلّيات.

قياس الأداء: mIoU لكلّ صنف

المقياس القياسي للتقطيع الدلالي هو mean Intersection over Union (mIoU): نحسب IoU لكلّ صنف على حدة، ثم نأخذ المتوسّط.

IoUc=TPcTPc+FPc+FNc\text{IoU}_c = \frac{TP_c}{TP_c + FP_c + FN_c}

مع TPcTP_c عدد بكسلات الصنف cc المُصنَّفة صحيحًا، وهكذا. مثال على تقاطع طرق:

الصنفIoU
طريق0.94
سماء0.91
مبانٍ0.82
سيّارة0.71
مُشاة0.38
mIoU0.752

الرقم الإجمالي 0.752 يُخفي حقيقة أساسية: النموذج ضعيف على المُشاة. حين تكون سلامة العابرين هي الأولوية، هذا التقرير يستدعي عملًا فوريًا (مزيد من صور المُشاة، وأوزان صنف، وتكثير أقوى).

استخدام U-Net مع segmentation_models_pytorch

import segmentation_models_pytorch as smp
import torch

# نموذج جاهز: U-Net بمشفر ResNet-34 مدرب مسبقا
model = smp.Unet(
encoder_name="resnet34",
encoder_weights="imagenet",
in_channels=3,
classes=5, # طريق، رصيف، سماء، مباني، مركبة
)

# خسارة مركبة: CE + Dice
ce_loss = torch.nn.CrossEntropyLoss()
dice_loss = smp.losses.DiceLoss(mode="multiclass")

def loss_fn(pred, target):
return 0.5 * ce_loss(pred, target) + 0.5 * dice_loss(pred, target)

# مرور امامي على دفعة من الصور
images = torch.randn(4, 3, 512, 512) # (B, C, H, W)
masks = torch.randint(0, 5, (4, 512, 512)) # اقنعة صحيحة

logits = model(images) # (B, 5, 512, 512)
loss = loss_fn(logits, masks)
loss.backward()
حواف الأقنعة تخدع mIoU

mIoU يُقاس بالبكسل، وبكسلات الحواف قليلة نسبةً إلى الجسم كلّه. نموذج يُنتج قناعًا في الموضع الصحيح لكن مُنعَّمًا على الحواف قد يُبلّغ عن mIoU جيّد وهو غير مفيد للتطبيقات التي تحتاج إلى حدود دقيقة (كقياس مساحة الطريق بدقّة سنتيمتر). لهذا يُستحسن تكميل mIoU بمقاييس حدود مثل Boundary IoU حين يكون شكل الحدود مهمًّا.

في الخلاصة

  • التقطيع الدلالي يُصنّف كلّ بكسل إلى صنف من مجموعة صارمة، بمعمارية مُشفِّر-فاكّ شفرة.
  • U-Net يستخدم وصلات التخطّي لاستعادة التفاصيل المكانية التي يُفقدها التقليص؛ DeepLab يعتمد على الالتفافات الموسّعة وASPP للاحتفاظ بدقّة عالية.
  • خسارة Dice أو IoU تُعالج عدم توازن الأصناف الحادّ بين الخلفية الشاسعة والأجسام الصغيرة كالمُشاة.
  • mIoU هو المقياس القياسي؛ اقرأه دائمًا لكلّ صنف، فمتوسّطًا وحده يُخفي فشل النموذج على الأصناف الأقلّ تمثيلًا.

الوحدة التالية: تقطيع النُسَخ مع Mask R-CNN، حيث نُميّز كلّ سيّارة على حدة، لا كلّ بكسل «سيّارة» بشكل عامّ.