nsr51324/DeepX-AI-Hackathon-ABSA
DeepX-AI-Hackathon-ABSA
A multi-dialect, multilingual Aspect-Based Sentiment Analysis (ABSA) system for Arabic reviews (Modern Standard Arabic, dialectal Arabic, Franco-Arabic, English, and French).
An ensemble of 4 independently fine-tuned transformer backbones, combined with a language-aware routing system, purpose-built for real-world user reviews (e.g. Google Maps, Play Store, food delivery apps) written in mixed scripts and dialects β including Egyptian, Gulf, and Levantine Arabic, and Franco-Arabic (Arabic written with Latin letters and digits).
π Overview
This project is a complete two-stage pipeline that extracts, for every review:
- Aspects mentioned in the review (e.g. food, service, price, cleanlinessβ¦).
- Sentiment associated with each individual aspect (positive / negative / neutral).
The final output for each review is a set of (aspect, sentiment) tuples:
{
"review_id": 12345,
"aspects": [
{"aspect": "food", "sentiment": "positive"},
{"aspect": "service", "sentiment": "negative"}
]
}Why an ensemble of 4 models?
Real-world Arabic reviews are far from uniform β the same user might write in Modern Standard Arabic, a regional dialect, Franco-Arabic (Latin letters + digits standing in for Arabic sounds), or plain English/French. To handle this diversity, four different backbones were fine-tuned, each with a different strength, and their outputs are combined via a language-routed, weighted soft-voting ensemble.
π§ Architecture
Stage 1 β Aspect Detection (Multi-Label Classification)
For every review text, the model predicts which of 9 aspect categories are mentioned:
Model architecture:
Review text β Backbone (BERT / RoBERTa) β [CLS] embedding
β
Metadata Fusion (concatenated with text embedding):
- Star rating β Embedding
- Business category β Embedding
- Platform (Google Maps / Play Store) β Embedding
β
MLP + LayerNorm + Dropout
β
Linear layer β 9 logits (multi-label)
β
Sigmoid + per-class decision thresholdStage 2 β Sentiment Classification (per aspect)
Once the aspects are extracted, for every (review, aspect) pair an aspect-aware question is built:
- Arabic backbones:
[ΩΨ¬ΩΩ =X] <text> [SEP] Ω Ψ§ Ψ±Ψ§ΩΩ ΩΩ <aspect> Ψ - Latin-script backbone (XLM-R):
[stars=X] <text> [SEP] what about the <aspect> ?
The pair is then classified into one of 3 classes: positive / negative / neutral.
(Text + aspect question) β Backbone β [CLS]
β
Metadata Fusion + Aspect Embedding
β
MLP (128) β 3 logits
β
Softmaxπ Language Router
Before any modeling, every text is automatically routed into one of the following categories using regex heuristics and marker-word dictionaries:
Important fix (V2): Very short texts (1β2 words) without a clear sentiment word (e.g. "Up" or "Shady") are not routed to Franco β they're routed to empty_rating_only instead, since model predictions on such short strings are less reliable than a simple star-based rule.Which backbones handle which route?
ROUTE_BACKBONES = {
'arabic': ['marbert', 'arabert', 'camelbert', 'xlmr'],
'mixed': ['marbert', 'camelbert', 'xlmr'],
'franco': ['marbert', 'arabert', 'camelbert', 'xlmr'],
'latin': ['xlmr'],
'other_script': ['xlmr'],
'empty_rating_only': [], # handled entirely by a hand-written star-based rule
}ποΈ Backbones
Training data notes:
MARBERTandXLM-Rwere trained on an expanded dataset: real Arabic reviews + synthetically generated Franco-Arabic variants (see below).AraBERTandCAMeLBERTwere trained on real Arabic data only.
π² Synthetic Franco-Arabic Data Augmentation
Since real Franco-Arabic examples are scarce in the training set, an automatic Arabic β Franco-Arabic converter was built, based on:
- A common-word dictionary (60+ frequent Arabic words/phrases mapped to their typical Franco-Arabic spellings, e.g.
Ω Ω ΨͺΨ§Ψ² β mumtaz/momtaz,Ω Ψ΄ β mesh/mish). - A character-level transliteration map for the remaining words (e.g.
Ψ β 7,ΨΉ β 3,ΨΊ β 8). - Controlled randomness (75% chance of using the common-word dictionary) to mimic natural spelling variation.
This expanded the MARBERT/XLM-R training set from 1,971 to 3,809 samples.
βοΈ Ensemble & Weight Tuning
After training the four backbones, a weighted soft-voting ensemble combines their probability outputs, weighted per model, and thresholded per aspect class.
Weights (from a grid search over 625 combinations on the validation set):
The fixed weights actually used for final test-set inference were: {'marbert': 1.2, 'arabert': 1.2, 'camelbert': 1.0, 'xlmr': 0.7} β see `ensemble_weights.json`.Per-aspect decision thresholds
Saved in `thresholds.npy`:
π Post-Processing Rules
- Empty / rating-only reviews (
empty_rating_only) skip the models entirely and are classified directly from the star rating: - β β₯ 4 β
general: positive - β β€ 2 β
general: negative - β = 3 β
none: neutral - Max 6 aspects per review (kept by highest predicted probability).
- If
noneco-occurs with other aspects,noneis dropped (a specific aspect and "no aspect" together are contradictory). - If no aspect crosses its threshold,
none: neutralis used as a default. - If a sentiment prediction is unavailable for a given aspect, the star rating is used as a fallback.
π Results (Validation Set β 1,971 reviews)
Main metric: Tuple F1 (aspect + sentiment must both match)
Performance by route
Performance by aspect
Sentiment confusion matrix (when the aspect is correctly detected)
π Repository Contents
DeepX-AI-Hackathon-ABSA/
βββ models/ # Weights for all 4 backbones (Stage 1 + Stage 2)
βββ ensemble_weights.json # Final ensemble weights
βββ thresholds.npy # Per-aspect decision thresholds (9 values)
βββ submission.json # Predictions on the unlabeled set
βββ submission_test.json # Predictions on the hidden test set
βββ __huggingface_repos__.json # Repository metadata
βββ README.md # This fileπ Usage
β οΈ This is not a single model loadable withAutoModeland a standardpipeline(). It is an ensemble of 4 backbones plus custom language-routing, preprocessing, and post-processing logic. Running inference requires the full inference code (from the original training notebook), not just the saved weights.
Inference outline:
from transformers import AutoTokenizer, AutoModel
import torch, json, numpy as np
BACKBONES = {
'marbert': 'UBC-NLP/MARBERTv2',
'arabert': 'aubmindlab/bert-base-arabertv02-twitter',
'camelbert': 'CAMeL-Lab/bert-base-arabic-camelbert-da',
'xlmr': 'FacebookAI/xlm-roberta-base',
}
# 1. Load the Stage-1 (aspect) and Stage-2 (sentiment) checkpoints from models/
# 2. Route each text via detect_language()
# 3. Preprocess it according to its route via preprocess_by_route()
# 4. Run the backbones listed in ROUTE_BACKBONES[route]
# 5. Combine outputs with the weights in ensemble_weights.json
# 6. Apply the per-aspect thresholds in thresholds.npy
# 7. Apply the post-processing rules to build the final predictionFor the complete code (model definitions, helper functions, preprocessing, and ensembling logic), see the original training notebook shipped alongside this project.
π― Intended Use
- Multi-dialect customer review analysis (Google Maps / Play Store / food-delivery platforms).
- Extracting per-aspect strengths and weaknesses (food, service, price, cleanliness, β¦) for business owners.
- Sentiment dashboards for restaurants, hotels, delivery apps, clinics, and e-commerce.
β οΈ Limitations
- Performance on very short / empty reviews (
empty_rating_only) is comparatively weaker (F1 = 0.61) since it relies purely on a star-rating rule rather than the model. - The
noneaspect has weaker performance (F1 = 0.68), reflecting the difficulty of distinguishing "no clear aspect" from a generic "general" comment. - Trained on only 1,971 labeled reviews β a relatively small dataset, which may limit generalization to domains not well represented in training (e.g. medical or real-estate reviews).
- Franco-Arabic training examples are synthetically generated rather than fully authentic, which may reduce accuracy on unusual real-world Franco-Arabic spelling patterns.
π Context
This model was developed as part of the DeepX AI Hackathon, addressing an Aspect-Based Sentiment Analysis (ABSA) task on multilingual, multi-dialect Arabic reviews.
π License
MIT
For questions about this model, please open a Discussion on the Hugging Face repository page.
