چیتشیت
حسابان، گرادیانها و بهینهسازی محدب
Calculus, Gradients and Convex Optimization
مشتقها، مشتقگیری خودکار، GD، تکانه، Adam، نیوتن و آزمونهای تحدب. پیادهسازی از صفر با Python و PyTorch.
فهرست مطالب
گذر رو به جلو و گام رو به عقب در یک نورون
معماریمشتقگیری خودکار پسرو در Value.backward
گامبهگام- ثبتهر عملیات یک
Valueجدید با گرههای فرزند و یک کلوژر_backwardمیسازد. - مرتبسازی
build_topoهر گره را پس از گرههایی که به آنها وابسته است قرار میدهد. - مقداردهی اولیه (Seed)تنظیم
self.grad = 1.0روی خروجی. این همان dy/dy = 1 است. - پیمایش معکوسفراخوانی
v._backward()برای هر گره بر اساس معکوس ترتیب توپولوژیک. - انباشتهر کلوژر با
+=به مقدار.gradاضافه میکند. متغیری که دوبار استفاده شود جمع مقادیر را میگیرد. - بازنشانیتنظیم
p.grad = 0.0برای تمام پارامترها قبل از فراخوانی بعدیloss.backward(). - بهروزرسانیاعمال
p.data -= lr * p.gradبرای هر پارامتر.
وظایف در کد
کار و کد| وظیفه | کد |
|---|---|
| تفاضل مرکزی | numerical_derivative(f, x, h=1e-7) |
| گرادیان با چندین ورودی | numerical_gradient(f, point, h=1e-7) |
| هسین f(x, y) | hessian_2d(f, x, y, h=1e-5) |
| بررسی گرادیان مشتقگیری خودکار | gradient_check(build_expr, x_val, h=1e-7) |
| شبکه XOR، با 4 گره پنهان | model = MLP([2, 4, 1]) |
| اجرای یک بهینهساز | optimize(optimizer, func, grad_func, start) |
| سنجش تحدب با نمونهبرداری | check_convexity(f, dim) |
| گامهای نیوتن در فضای 2 بعدی | newtons_method(grad_f, hessian_f, x0) |
بهینهسازها از صفر
کدpython
GradientDescent(lr=0.001) # w = w - lr * gradient
SGDMomentum(lr=0.001, momentum=0.9) # v = beta * v + gradient
Adam(lr=0.001, beta1=0.9, beta2=0.999, epsilon=1e-8) # دو گشتاور به ازای هر وزن
m_hat = [m / (1 - self.beta1 ** self.t) for m in self.m] # تصحیح سوگیری
p - self.lr * mh / (vh ** 0.5 + self.epsilon) # اندازهی گام اختصاصی برای هر وزن
adam_history = optimize(Adam(lr=0.01), rosenbrock, rosenbrock_gradient, start)
مشتقگیری خودکار و بهینهسازها در PyTorch
کدpython
x = torch.tensor(2.0, requires_grad=True)
y = x ** 2 + 3 * x + 1
y.backward() # حالت پسرو از میان گراف ثبتشده
print(x.grad) # 7.0 = 2*x + 3
sgd = torch.optim.SGD(model.parameters(), lr=0.01, momentum=0.9)
adam = torch.optim.Adam(model.parameters(), lr=0.001)
adamw = torch.optim.AdamW(model.parameters(), lr=0.001, weight_decay=0.01)
scheduler = torch.optim.lr_scheduler.CosineAnnealingLR(adam, T_max=100)
فرمولهای کلیدی
مفهومها- تفاضل مرکزی
- $f'(x) \approx \frac{f(x + h) - f(x - h)}{2h}$.
- قاعدهی زنجیرهای
- $\frac{dy}{dx} = f'(g(x)) \cdot g'(x)$. جمع تمام مسیرها در نقاط انشعاب (branch) گراف.
- گرادیان کاهشی
- $w = w - \text{lr} \cdot \text{gradient}$.
- تکانه
- $v = \beta \cdot v + \text{gradient}$، سپس $w = w - \text{lr} \cdot v$.
- Adam
- $w = w - \text{lr} \cdot \hat{m} / (\sqrt{\hat{v}} + \epsilon)$ همراه با گشتاورهای تصحیحسوگیریشده.
- نیوتن
- $x_{\text{new}} = x - H^{-1} \cdot \text{gradient}$.
- محدب
- $f(tx + (1-t)y) \le t f(x) + (1-t) f(y)$ به ازای $t \in [0, 1]$.
- لاگرانژی
- $L(x, \lambda) = f(x) + \lambda g(x)$. گرادیان آن برابر صفر قرار داده میشود.
مشتقهای مهم که باید بدانید
دستورها| دستور | کاربرد |
|---|---|
x^2 | 2x. تابع زیان (loss) مبتنی بر MSE |
wx + b | x برای w، 1 برای b، w برای x. لایهی خطی |
e^x | e^x. سافتمکس، اتنشن |
ln(x) | 1/x. تابع زیان (loss) آنتروپی متقاطع |
sigmoid | f(x)(1-f(x)). فعالساز سیگموئید |
tanh | 1 - tanh^2. تابع فعالساز کلاسیک |
x^n | n x^(n-1). مورد استفاده در __pow__ |
sin(x^2) | cos(x^2) * 2x. مثالی از قاعدهی زنجیرهای |
انتخاب روش
دستورها| دستور | کاربرد |
|---|---|
Gradient descent | مشتقهای مرتبه اول. حافظه O(n). خط مبنا |
SGD with momentum | بهترین دقت نهایی با تیونینگ بیشتر |
Adam | انحنای قطری از روی گشتاورهای گرادیان. گزینهی پیشفرض یادگیری عمیق |
AdamW | Adam با کاهش وزن مجزا. مدلهای ترنسفورمر |
Newton's method | هسین کامل. پیچیدگی O(n^3) به ازای هر گام. مسائل محدب کوچک |
L-BFGS | تفاضلهای m گرادیان آخر. مسائل محدب متوسط |
K-FAC | تقریب فیشر فاکتورگیریشدهی کرونکر. آموزش با دستههای بزرگ |
اعداد و مقادیر پیشفرض
پیشفرضها| تنظیم | پیشفرض | یادداشت |
|---|---|---|
Adam `lr` | 0.001 | نقطهی شروع برای اکثر مسائل |
Adam `beta2` | 0.999 | beta1 برابر 0.9 است. نرخهای زوال گشتاور |
Adam `epsilon` | 1e-8 | جلوگیری از تقسیم بر صفر |
SGD momentum `lr` | 0.01 | با تکانهی 0.9 |
AdamW `weight_decay` | 0.01 | مجزا از گام گرادیان |
Mini-batch size | 32-256 | تخمین گرادیان مناسب با نویز متعادل |
Finite difference `h` | 1e-7 | در numerical_derivative |
Gradient check difference | < 1e-5 | مقایسهی مشتقگیری خودکار در برابر روش عددی |
عیبیابی
عیبیابیتابع زیان (loss) رشد میکند یا nan میشود
- علت
- نرخ یادگیری بسیار بزرگ است
- راهحل
- کاهش نرخ یادگیری
سرعت آموزش بسیار پایین است
- علت
- نرخ یادگیری بسیار کوچک است
- راهحل
- افزایش آن؛ افزودن برنامهی زمانبندی نرخ یادگیری
حرکت زیگزاگی در درههای باریک
- علت
- عدد حالت بالای ماتریس هسین
- راهحل
- افزودن تکانه، یا استفاده از روش نیوتن
گرادیان نزدیک به 0 بدون پیشرفت
- علت
- نقطهی زینی
- راهحل
- تکانه و نویز ناشی از دستههای کوچک
رشد تصاعدی گرادیانها در هر گام
- علت
- انباشت در
.gradبا استفاده از+= - راهحل
- تنظیم
p.grad = 0.0قبل ازbackward
اختلاف میان مشتقگیری خودکار و عددی
- علت
- باگ در قاعدهی
_backward - راهحل
- اجرای
gradient_check
مشتق مرتبهی دوم پر از نویز است
- علت
- اندازهی گام h بسیار کوچک است
- راهحل
- استفاده از
h=1e-4برای هر دو فراخوانی
هزینهی بالای نیوتن برای مدلهای بزرگ
- علت
- حافظه O(n^2) و معکوسسازی O(n^3)
- راهحل
- استفاده از L-BFGS یا Adam
پرسشها
پرسش و پاسخ- چرا حالت پسرو برای شبکهها؟
- ورودیهای بسیار و یک تابع زیان (loss) واحد. یک گام رو به عقب تمام گرادیانها را محاسبه میکند.
- چگونه تحدب را بسنجیم؟
- مشتق دوم >= 0 در فضای 1 بعدی؛ هسین مثبت نیمهمعین در ابعاد بالاتر.
- چرا SGD روی توابع زیان (loss) غیرمحدب کار میکند؟
- اکثر نقاط بحرانی، نقاط زینی هستند و بیشتر کمینهها عملکرد مناسبی دارند.
- چرا L1 وزنهای تنک تولید میکند؟
- شکل لوزی در امتداد محورها دارای گوشههای نوکتیز است.
- سستی مکمل چیست؟
- $\lambda_i \, g_i(x) = 0$. در بردارهای پشتیبان مقدار $\lambda > 0$ است.
نکات
نکتهها- برای آموزشهای طولانیتر از چند دوره (epoch)، از برنامهی زمانبندی نرخ یادگیری استفاده کنید.
- تبرید کسینوسی و گرمکردن مناسب مدلهای ترنسفورمر و شبکههای بزرگ هستند.
- روش نیوتن مسائل درجه دوم را تنها در یک گام حل میکند.
- بررسی گرادیان نیازمند 2 گذر رو به جلو به ازای هر پارامتر است؛ آن را در محیط عملیاتی اجرا نکنید.
- وجود مقادیر ویژه با علامتهای مختلف در ماتریس هسینِ یک نقطهی بحرانی، نشاندهندهی نقطهی زینی است.
- کمینههای تخت نسبت به کمینههای نوکتیز تعمیمپذیری بهتری دارند.