الگوریتم کلونی مورچگان (ACO): الهام‌گیری از طبیعت برای حل مسائل بهینه‌سازی 🐜✨

الگوریتم کلونی مورچگان (ACO): الهام‌گیری از طبیعت برای حل مسائل بهینه‌سازی 🐜✨

الگوریتم کلونی مورچگان (Ant Colony Optimization) یک روش فراابتکاری (Metaheuristic) است که از رفتار هوشمندانه مورچه‌ها در یافتن کوتاه‌ترین مسیر به منبع غذا الهام گرفته شده. این الگوریتم در سال ۱۹۹۲ توسط مارکو دوریگو معرفی شد و امروزه به یکی از قدرتمندترین ابزارها برای حل مسائل بهینه‌سازی ترکیباتی مانند مسیر یابی، زمان‌بندی و خوشه‌بندی تبدیل شده است.

🔍 ایده اصلی: چگونه مورچه‌ها مسیر بهینه را پیدا می‌کنند؟

مورچه‌ها با ترشح فرومون روی مسیرها، به یکدیگر سیگنال می‌دهند. هرچه مسیر کوتاه‌تر باشد، فرومون بیشتری روی آن باقی می‌ماند و مورچه‌های بعدی احتمال بیشتری برای انتخاب آن مسیر دارند. این فرآیند یک مکانیزم فیدبک مثبت ایجاد می‌کند که به طور طبیعی به راه‌حل بهینه همگرا می‌شود.


⚙️ مراحل الگوریتم ACO

۱. پارامترهای کلیدی

پارامتر توضیح
فرومون (τ) میزان جذابیت مسیر
قابلیت دید (η) اطلاعات اکتشافی (مثلاً معکوس فاصله)
α و β وزن فرومون و قابلیت دید
تبخیر فرومون (ρ) نرخ کاهش فرومون در هر تکرار

۲. گام‌های اجرا

  1. مقداردهی اولیه:

    • قرار دادن مورچه‌ها در نقاط شروع

    • مقدار اولیه فرومون برای همه مسیرها

  2. ساخت راه‌حل:
    هر مورچه با احتمال زیر مسیر را انتخاب می‌کند:

    P(i,j) = [τ(i,j)]^α * [η(i,j)]^β / Σ [τ(i,k)]^α * [η(i,k)]^β
  3. به‌روزرسانی فرومون:

    • تبخیر: τ(i,j) = (1-ρ) * τ(i,j)

    • تقویت: τ(i,j) += Σ (Q/Lₖ) برای مورچه‌هایی که از مسیر عبور کردند

  4. تکرار: تا رسیدن به شرط توقف (تعداد تکرار یا همگرایی)


📊 مثال کاربردی: حل مسئله فروشنده دوره‌گرد (TSP)

فرض کنید ۵ شهر با فواصل زیر داریم:

شهر A B C D E
A 0 2 5 1 3
B 2 0 4 6 2
C 5 4 0 3 7
D 1 6 3 0 4
E 3 2 7 4 0

اجرای ACO:

  • مورچه ۱: A → D → C → B → E → A (مسافت = 1+3+4+2+3 = 13)

  • مورچه ۲: A → B → E → D → C → A (مسافت = 2+2+4+3+5 = 16)

  • به‌روزرسانی فرومون: تقویت مسیرهای مورچه ۱


💻 پیاده‌سازی در پایتون


import numpy as np

class ACO_TSP:
    def __init__(self, distances, n_ants=10, n_iter=100, alpha=1, beta=2, rho=0.1, Q=1):
        self.distances = distances
        self.n_ants = n_ants
        self.n_iter = n_iter
        self.alpha = alpha
        self.beta = beta
        self.rho = rho
        self.Q = Q
        self.n_cities = len(distances)
        self.pheromone = np.ones((self.n_cities, self.n_cities))

    def run(self):
        best_path = None
        best_distance = float('inf')
        
        for _ in range(self.n_iter):
            paths = self._build_paths()
            self._update_pheromone(paths)
            
            current_best = min(paths, key=lambda x: x[1])
            if current_best[1] < best_distance:
                best_path, best_distance = current_best
                
        return best_path, best_distance

    def _build_paths(self):
        paths = []
        for _ in range(self.n_ants):
            path = [0]  # شروع از شهر 0
            visited = set([0])
            
            while len(path) < self.n_cities:
                current = path[-1]
                probs = []
                for city in range(self.n_cities):
                    if city not in visited:
                        phe = self.pheromone[current][city] ** self.alpha
                        eta = (1 / self.distances[current][city]) ** self.beta
                        probs.append(phe * eta)
                    else:
                        probs.append(0)
                        
                probs = np.array(probs) / sum(probs)
                next_city = np.random.choice(range(self.n_cities), p=probs)
                path.append(next_city)
                visited.add(next_city)
            
            path.append(0)  # بازگشت به شهر شروع
            distance = sum(self.distances[path[i]][path[i+1]] for i in range(len(path)-1))
            paths.append((path, distance))
            
        return paths

    def _update_pheromone(self, paths):
        self.pheromone *= (1 - self.rho)  # تبخیر
        for path, distance in paths:
            contribution = self.Q / distance
            for i in range(len(path)-1):
                self.pheromone[path[i]][path[i+1]] += contribution

# مثال:
distances = [
    [0, 2, 5, 1, 3],
    [2, 0, 4, 6, 2],
    [5, 4, 0, 3, 7],
    [1, 6, 3, 0, 4],
    [3, 2, 7, 4, 0]
]

aco = ACO_TSP(distances, n_ants=15, n_iter=200)
best_path, best_distance = aco.run()
print(f"بهترین مسیر: {best_path}، کمترین مسافت: {best_distance}")


🌐 کاربردهای ACO

✅ مسیریابی شبکه‌های کامپیوتری
✅ زمان‌بندی کارها در تولید صنعتی
✅ خوشه‌بندی داده‌ها
✅ بهینه‌سازی پورتfolio مالی
✅ طراحی مدارهای VLSI


📈 مزایا و معایب

مزایا معایب
مناسب برای مسائل دینامیک نیاز به تنظیم پارامترها (α, β, ρ)
موازی‌سازی آسان زمان اجرای بالا برای مسائل بزرگ
مقاوم در برابر مینیماهای محلی وابستگی به مقداردهی اولیه فرومون

🔮 توسعه‌های جدید در ACO

  • ACO هیبرید: ترکیب با الگوریتم‌های دیگر مانند شبکه‌های عصبی

  • ACO چند هدفه: بهینه‌سازی همزمان چند تابع هدف

  • ACO مبتنی بر جمعیت: بهبود همگرایی با حافظه جمعیتی


📚 منابع پیشنهادی

  1. کتاب: "Ant Colony Optimization" توسط Marco Dorigo و Thomas Stützle

  2. مقاله اصلی: The Ant System: Optimization by a colony of cooperating agents

  3. دوره آموزشی: ACO in Python – Udemy

سوال تفکربرانگیز:
اگر فرومون می‌توانست هم جذب کننده و هم دفع کننده باشد، چگونه الگوریتم تغییر می‌کرد؟ ایده‌های خود را به اشتراک بگذارید!

Avatar

نویسنده

سیدهادی موسوی

تعداد لایک‌ها: 2

Tags: #علمی #تئوری #برنامه_نویسی #مقاله

ارسال نظر

نظرات