
Zincir Kuralı (Chain Rule), bir değişkenin başka bir değişkeni, onun da başka bir değişkeni etkilediği birbirine bağlı sistemlerde, başlangıçtaki küçük bir değişikliğin zincirin sonundaki sonucu ne kadar değiştireceğini hesaplamamızı sağlayan Kalkülüs'ün en önemli kurallarından biridir. Tek başına Türev bize bir fonksiyonun değişim hızını, Kısmi Türevler birden fazla değişken olduğunda her değişkenin etkisini, Gradyan ise bütün bu değişim yönlerini tek bir vektörde göstermeyi öğretti. Fakat gerçek sistemlerde değişkenler çoğu zaman birbirlerinden bağımsız değildir. Bir değişken diğerini, o başka bir değişkeni, o da nihai sonucu etkiler. Bu makalede fonksiyon bileşkesinden başlayarak Zincir Kuralının sezgisel anlamını, tek ve çok değişkenli fonksiyonlarda nasıl kullanıldığını, birden fazla bağımlılık yolunun nasıl birleştiğini ve son olarak modern yapay sinir ağlarının öğrenme mekanizmasının temelinde neden Zincir Kuralının bulunduğunu inceleyeceğiz.
Zincir Kuralına Neden İhtiyacımız Var?
Bir önceki makalemizin sonunda çok önemli bir problem bırakmıştık.
Elimizde:
şeklinde iki değişkenli bir fonksiyon olsun.
Fakat \(x\) ve \(y\) birbirlerinden bağımsız olmasınlar. Her ikisi de başka bir \(t\) değişkenine bağlı olsun:
ve:
Bu durumda ortaya şöyle bir bağımlılık zinciri çıkar:
ve ardından:
\(t\)'yi biraz değiştirdiğimizde \(x\) değişir. Aynı anda \(y\) de değişir. \(x\) ve \(y\)'deki bu değişimler de \(z\)'yi değiştirir.
Dolayısıyla artık yalnızca \(\frac{\partial z}{\partial x}\) veya \(\frac{\partial z}{\partial y}\) bilmek yeterli değildir. Bizim asıl bilmek istediğimiz \(\frac{dz}{dt}\) değeridir.
Yani: \(t\)'de meydana gelen küçücük bir değişiklik, bütün ara değişkenlerden geçtikten sonra \(z\)'yi ne kadar değiştiriyor?
Zincir Kuralının cevap verdiği temel soru budur.
Bileşke Fonksiyonları Hatırlayalım
Fonksiyonlar makalemizde bileşke fonksiyonları görmüştük.
Örneğin:
ve:
olsun.
Önce \(g\), ardından onun sonucu üzerinde \(f\) çalıştırılırsa:
elde ederiz.
Yani:
olur.
Burada aslında iki aşamalı bir sistem vardır:
Bunu biraz daha açık yazmak için ara değişkene \(u\) diyebiliriz:
ve:
Bu durumda sistemimiz:
haline gelir.
Şimdi şu soruyu soralım: \(x\)'te meydana gelen küçük bir değişim \(y\)'yi ne kadar değiştirir?
Bunu anlamak için zincirin iki parçasına ayrı ayrı bakabiliriz.
İlk olarak \(\frac{du}{dx}\) bize \(x\)'teki değişimin \(u\)'yu ne kadar değiştirdiğini söyler.
Ardından \(\frac{dy}{du}\) bize \(u\)'daki değişimin \(y\)'yi ne kadar değiştirdiğini söyler.
O halde \(x\)'in \(y\) üzerindeki toplam etkisini bulmak için bu iki değişim oranını birleştirmemiz gerekir.
Zincir Kuralı tam olarak bunu yapar:
İki değişim oranı birbiriyle çarpılır.
Bu çarpım Zincir Kuralının özüdür.
Değişimler Neden Çarpılıyor?
Formülü ezberlemek kolaydır. Fakat neden çarpım olduğunu anlamak çok daha önemlidir.
Bir sistem düşünelim.
\(x\)'te küçük bir değişiklik yapalım:
\(x\)'teki bu değişimin \(u\)'ya yaklaşık etkisi:
olacaktır.
Şimdi \(u\)'daki değişim \(y\)'yi etkilesin:
Birinci ifadeyi ikinci ifadede yerine koyarsak:
dolayısıyla:
elde ederiz.
Her iki tarafı \(\Delta x\)'e bölersek:
ve değişimler sonsuz derecede küçüldüğünde:
sonucuna ulaşırız.
Dolayısıyla Zincir Kuralındaki çarpım rastgele ortaya çıkmış bir işlem değildir. Bir değişimin başka bir değişim üzerinden aktarılmasının doğal sonucudur.
Bunu günlük bir örnekle düşünelim.
Bir makinenin girişini %2 artırdığımızda ara çıktısı %3 artıyor olsun. Ara çıktının %1 artması da nihai çıktıyı %4 artırıyor olsun. Başlangıçtaki değişim ara sistem tarafından büyütülüyor, ardından ikinci sistem tarafından tekrar ölçekleniyor. Bir değişim başka bir değişim mekanizmasından geçerken etkiler birbirleriyle çarpılır. Zincir Kuralı, bunun matematiksel biçimidir.
İlk Zincir Kuralı Örneğimiz
Şimdi:
fonksiyonunun türevini hesaplayalım.
Bu fonksiyonun içerisinde başka bir fonksiyon bulunduğunu görebiliyoruz.
İç fonksiyona:
diyelim.
Bu durumda:
olur.
Artık iki basit türev alabiliriz.
Dış fonksiyon:
için:
İç fonksiyon:
için ise:
olur.
Zincir Kuralını uygulayalım:
Yerlerine koyarsak:
elde ederiz.
Fakat sonucumuzda artık \(u\) değişkenini istemiyoruz.
olduğuna göre:
ve sonuç:
olur.
İstersek açabiliriz:
Bu örnek Zincir Kuralının pratik kullanımını çok güzel gösterir.
Önce dış fonksiyonun türevini alıyoruz, ardından iç fonksiyonun türeviyle çarpıyoruz.
Dışarıdan İçeri Doğru
Tek değişkenli fonksiyonlarda Zincir Kuralını kullanırken akılda tutulabilecek basit bir yöntem vardır:
Dış fonksiyonun türevini al, içini olduğu gibi bırak, sonra iç fonksiyonun türeviyle çarp.
Örneğin:
fonksiyonunu ele alalım.
Dış fonksiyon:
iç fonksiyon ise:
şeklindedir.
Dış fonksiyonun türevi:
olur.
\(u\)'yu tekrar yerine koyarsak:
elde ederiz.
Fakat henüz işimiz bitmedi.
İç fonksiyonun türevi:
olduğuna göre:
ve:
sonucuna ulaşırız.
Buradaki \(2x\) ifadesini unutmak, Zincir Kuralında yapılan en yaygın hatalardan biridir.
Zincir Daha Uzunsa Ne Olur?
Fonksiyonların yalnızca iki katmandan oluşması gerekmez.
Örneğin:
fonksiyonunu ele alalım.
Burada üç ayrı dönüşüm vardır.
Önce:
Ardından:
Son olarak:
Dolayısıyla zincir:
şeklindedir.
\(x\)'in \(y\) üzerindeki etkisini hesaplamak istiyorsak:
yazarız.
Şimdi her parçayı hesaplayalım.
Dolayısıyla:
olur.
Önce \(v\)'yi:
ve \(u\)'yu:
yerine koyarsak:
sonucuna ulaşırız.
Burada çok önemli bir yapı ortaya çıkmış oluyor: Zincir ne kadar uzun olursa olsun fikir değişmez.
Bu fikir ileride yapay sinir ağları açısından son derece önemli hale gelecek.
Üstel Fonksiyonlarda Zincir Kuralı
Türev makalemizde:
olduğunu görmüştük.
Fakat üs yalnızca \(x\) değilse ne olacak?
Örneğin:
olsun.
İç fonksiyonu:
olarak tanımlayalım.
Bu durumda:
olur.
Dış fonksiyonun türevi:
İç fonksiyonun türevi:
olduğuna göre:
ve:
elde ederiz.
Genel olarak:
ise:
olur.
Bu formül özellikle makine öğrenmesinde kullanılan aktivasyon, olasılık ve maliyet fonksiyonlarının türevlerinde sürekli karşımıza çıkar.
Logaritmik Fonksiyonlarda Zincir Kuralı
Doğal logaritmanın türevini:
olarak öğrenmiştik.
Şimdi:
fonksiyonunu ele alalım.
İç fonksiyon:
olsun.
Dış fonksiyon:
olduğuna göre:
ve:
olur.
Zincir Kuralıyla:
Dolayısıyla:
elde ederiz.
Genel olarak:
ise:
olur.
Trigonometrik Fonksiyonlarda Zincir Kuralı
Aynı yapı trigonometrik fonksiyonlarda da geçerlidir.
Örneğin:
olsun.
İç fonksiyon:
ve dış fonksiyon:
olur.
Buna göre:
ve:
olduğundan:
ve:
elde ederiz.
Genel olarak:
Benzer şekilde:
olur.
Burada tekrar aynı deseni görüyoruz. Dışarıdaki fonksiyon değişiyor. Fakat Zincir Kuralının mantığı değişmiyor.
Zincir Kuralı ile Diğer Türev Kuralları Birlikte Kullanılabilir
Gerçek fonksiyonlar çoğu zaman yalnızca tek bir kural gerektirmez.
Örneğin:
fonksiyonunun türevini düşünelim.
Burada iki fonksiyon çarpıldığı için Çarpım Kuralına ihtiyacımız vardır.
Fakat:
ifadesinin içerisinde de bileşke fonksiyon bulunduğu için Zincir Kuralına ihtiyacımız vardır.
Çarpım Kuralı:
olduğuna göre:
yazarız.
Şimdi Zincir Kuralıyla:
olur.
Dolayısıyla:
elde ederiz.
Yani türev kuralları birbirlerinin alternatifi değildir. Bir fonksiyonun yapısına göre aynı işlem içerisinde birden fazla kural birlikte kullanılabilir.
Leibniz Gösteriminin Gücü
Zincir Kuralı özellikle Leibniz gösterimi kullanıldığında oldukça sezgisel görünür.
Elimizde:
zinciri olsun.
Zincir Kuralı:
şeklindedir.
İlk bakışta \(du\) ifadeleri birbirini sadeleştiriyormuş gibi görünür:
Bu gösterim Zincir Kuralını hatırlamak açısından oldukça kullanışlıdır.
Ancak burada önemli bir ayrıntı vardır.
Türev ifadeleri sıradan kesirler değildir. Dolayısıyla matematiksel gerekçe gerçekten "\(du\)'ları sadeleştirmek" değildir. Leibniz gösterimi yalnızca değişkenler arasındaki bağımlılık yapısını olağanüstü güzel biçimde görünür hale getirir. Asıl sebep, biraz önce küçük değişimler üzerinden gördüğümüz gibi yerel değişim oranlarının birbirleriyle çarpılmasıdır.
Belirli Bir Noktada Zincir Kuralı
Şimdi Zincir Kuralını belirli bir noktadaki değişim üzerinden inceleyelim.
Fonksiyonumuz:
olsun.
Türev:
yani:
olur.
Şimdi \(x=1\) noktasına bakalım.
elde ederiz.
Bu sayı bize \(x=1\) yakınında \(x\)'te yapılacak çok küçük bir değişikliğin \(y\)'de yaklaşık 24 katı büyüklüğünde bir değişim oluşturacağını söyler.
Örneğin:
ise yerel doğrusal yaklaşım kullanarak:
yani:
diyebiliriz.
Zincir Kuralı yalnızca sembolleri türevlemek için kullanılan mekanik bir yöntem değildir. Aslında bir sistem içerisindeki duyarlılığın nasıl yayıldığını hesaplamaktadır.
Bu kelimeyi aklımızda tutalım: Duyarlılık.
Bir değişkendeki küçük hareketin başka bir değişkeni ne kadar etkilediği.
Yapay sinir ağlarına geldiğimizde yaptığımız şey tam olarak bu olacak.
Çok Değişkenli Zincir Kuralı
Şimdi bir önceki makalemizin bıraktığı probleme geri dönelim.
Elimizde:
fonksiyonu olsun.
Fakat:
ve:
olsun.
Dolayısıyla \(t\), \(z\)'yi iki farklı yoldan etkilemektedir:
ve:
Birinci yolun etkisi:
olur.
İkinci yolun etkisi ise:
olur.
\(t\)'nin \(z\) üzerindeki toplam etkisini hesaplamak için iki yolun katkısını toplarız:
İşte çok değişkenli Zincir Kuralının en temel biçimi budur. Burada çok önemli yeni bir fikir ortaya çıkıyor.
Aynı değişken sonucu birden fazla farklı yoldan etkileyebiliyorsa:
Her yol üzerindeki değişimler çarpılır, farklı yolların etkileri ise toplanır.
Bunu şöyle özetleyebiliriz:
Bu iki cümle, yalnızca Zincir Kuralını değil, birazdan göreceğimiz geri yayılım algoritmasının da özünü oluşturacak.
Çok Değişkenli Bir Örnek
Bir önceki makalemizde kullandığımız fonksiyona benzeyen:
fonksiyonunu ele alalım.
Fakat bu kez \(x\) ve \(y\) bağımsız olmasın.
ve:
olsun.
Amacımız \(\frac{dz}{dt}\) değerini hesaplamak.
Önce \(z\)'nin kısmi türevlerini bulalım.
\(x\)'e göre:
\(y\)'ye göre:
Şimdi \(x\) ve \(y\)'nin \(t\)'ye göre türevlerini hesaplayalım.
ve:
Çok değişkenli Zincir Kuralı:
olduğuna göre:
elde ederiz.
Şimdi örneğin:
noktasındaki değişim hızını hesaplayalım.
Önce:
ve:
olur.
Kısmi türevler:
ve:
olur.
Aynı noktada:
ve:
olduğundan:
sonucuna ulaşırız.
Yani \(t=1\) noktasında \(t\)'de meydana gelen küçük bir değişimin \(z\) üzerindeki toplam etkisi yaklaşık 40 katıdır.
Fakat burada güzel bir doğrulama da yapabiliriz.
Sonucu Doğrudan Doğrulayalım
Elimizde:
vardı.
Ayrıca:
ve:
olduğunu biliyoruz.
Bunları doğrudan \(z\)'de yerine koyabiliriz:
Parantezleri açalım:
Dolayısıyla:
olur.
Şimdi doğrudan \(t\)'ye göre türev alalım:
\(t=1\) için:
çıkar.
Zincir Kuralıyla bulduğumuz sonuçla tamamen aynıdır.
Burada Zincir Kuralının bize sağladığı avantaj henüz çok büyük görünmeyebilir. Çünkü bütün değişkenleri yerine koyup fonksiyonu doğrudan sadeleştirebildik. Fakat yüzlerce, binlerce veya milyonlarca ara değişken bulunan bir sistemde bunu yapmak mümkün olmayacaktır.
İşte Zincir Kuralının gerçek gücü orada ortaya çıkar.
Daha Fazla Değişken Olduğunda
Fonksiyonumuz:
olsun.
Her \(x_i\) değişkeni de \(t\)'ye bağlıysa:
Zincir Kuralı genel olarak:
şeklinde yazılabilir.
Açık biçimiyle:
olur.
Bir önceki makalemizde Gradyanı:
şeklinde tanımlamıştık.
Aynı şekilde değişkenlerin \(t\)'ye göre değişimlerini:
vektörüyle ifade edebiliriz.
Bu durumda Zincir Kuralı:
şeklinde yazılabilir.
Tanıdık geldi mi?
Bu tam olarak bir nokta çarpım işlemidir.
Serimizin başında öğrendiğimiz Vektörler ve Nokta Çarpım kavramı, Türev ve Gradyan üzerinden yeniden karşımıza çıktı.
Matematiğin birbirinden bağımsız gibi görünen parçaları bir kez daha aynı yapının içerisinde birleşiyor.
Toplam Türev
Burada \(\frac{dz}{dt}\) ifadesine bazen toplam türev (total derivative) denir.
Bunun sebebi önemlidir.
Kısmi türev:
hesaplanırken yalnızca \(x\)'in değiştiğini, diğer değişkenlerin sabit kaldığını varsayıyorduk.
Fakat toplam türevde:
hesaplanırken \(t\)'nin değiştirdiği bütün değişkenlerin katkısını dikkate alıyoruz.
Yani kısmi türev:
Diğer her şey sabitken \(x\) değişirse ne olur?
sorusunu sorar.
Toplam türev ise:
\(t\) değiştiğinde ona bağlı bütün değişkenler birlikte hareket ederse sonuçta ne olur?
sorusunu cevaplar.
Gerçek fiziksel sistemlerde ve yapay zeka modellerinde çoğu zaman ihtiyacımız olan şey ikinci sorunun cevabıdır.
Bağımlılıkları Bir Grafik Olarak Düşünmek
Zincir Kuralını anlamanın en güçlü yollarından biri fonksiyonları yalnızca formül olarak değil, bir hesaplama grafiği (Computational Graph) olarak düşünmektir.
Basit:
fonksiyonumuzu yeniden ele alalım.
Bu fonksiyon aslında şu işlemlerden oluşur:
Her düğüm küçük bir hesaplama yapar.
Her bağlantı ise bir değişkenin başka bir değişkeni etkilediğini gösterir.
Daha genel olarak:
şeklinde bir grafik düşünelim.
Her bağlantının üzerinde yerel bir türev vardır:
Başlangıçtaki \(x\)'in en sondaki \(y\) üzerindeki etkisi ise yol üzerindeki bu yerel türevlerin çarpımıdır:
Bu bakış açısı Zincir Kuralını bambaşka bir seviyede anlamamızı sağlar.
Artık devasa bir fonksiyonun tamamının türevini tek seferde hesaplamak zorunda değiliz.
Her küçük işlemin yerel türevini biliyorsak, bunları birbirine bağlayarak bütün sistemin türevini hesaplayabiliriz.
Bir Değişken Sonucu Birden Fazla Yoldan Etkilerse
Biraz daha ilginç bir hesaplama grafiği düşünelim.
ve:
olsun.
Burada \(x\), \(y\)'yi iki farklı yol üzerinden etkilemektedir:
ve:
Birinci yol üzerindeki etki:
ikinci yol üzerindeki etki ise:
olur.
Toplam etkiyi bulmak için bu iki yolun katkısını toplarız:
Şimdi her parçayı hesaplayalım.
Dolayısıyla:
olur.
\(u=x^2\) ve \(v=3x\) değerlerini yerine koyarsak:
ve:
sonucuna ulaşırız.
Bunu doğrudan da doğrulayabiliriz.
olduğuna göre:
elde ederiz.
Burada daha önce öğrendiğimiz Çarpım Kuralının aslında Zincir Kuralının hesaplama grafiği üzerindeki doğal bir sonucu olduğunu görebiliriz.
Bir değişken sonuca birden fazla yoldan ulaşıyorsa her yol üzerindeki yerel türevler çarpılır ve bütün yolların katkıları toplanır.
Bu fikir karmaşık görünse de özü son derece basittir:
Jacobian Matrisi
Şimdiye kadar çoğunlukla birden fazla girdisi fakat tek bir çıktısı bulunan fonksiyonlarla çalıştık.
Örneğin:
Bu tür bir fonksiyonun bütün kısmi türevlerini Gradyan içerisinde bir araya getirebiliyorduk:
Fakat bir fonksiyonun birden fazla çıktısı da olabilir.
Örneğin:
olsun.
Artık iki girdimiz ve iki çıktımız vardır.
Her çıktının her girdiye göre nasıl değiştiğini bilmek istiyoruz.
Bu durumda dört ayrı kısmi türeve ihtiyacımız olur:
Bu türevleri tek bir yapı içerisinde topladığımız matrise Jacobian matrisi denir.
Jacobianın her satırı bir çıktının girdilere karşı duyarlılığını gösterir.
Her sütunu ise belirli bir girdinin bütün çıktılar üzerindeki etkisini gösterir.
Daha genel olarak:
şeklinde \(n\) girdili ve \(m\) çıktılı bir fonksiyon için Jacobian:
şeklindedir.
Dolayısıyla Jacobian, çok sayıda giriş ve çıkış arasındaki bütün yerel değişim ilişkilerini tek bir matriste saklar.
Bir Jacobian Hesaplayalım
Şu vektör değerli fonksiyonu ele alalım:
Burada:
ve:
olur.
Önce birinci çıktının kısmi türevlerini hesaplayalım:
İkinci çıktı için:
olur.
Bu türevleri Jacobian matrisine yerleştirirsek:
elde ederiz.
Örneğin \((x,y)=(2,3)\) noktasında:
olur.
Bu matris, \((2,3)\) noktasının yakınında girdilerdeki küçük değişimlerin iki çıktıya nasıl taşınacağını söyler.
Girdilerdeki küçük değişimi:
şeklinde gösterirsek çıktılardaki yaklaşık değişim:
olur.
Yani Jacobianı, bir fonksiyonun belirli bir noktanın yakınındaki doğrusal davranışını temsil eden dönüşüm matrisi olarak düşünebiliriz.
Jacobian ile Zincir Kuralı
Şimdi iki vektör değerli fonksiyonun birbirine bağlandığını düşünelim.
ve:
olsun.
Bu durumda:
şeklinde bir bağımlılık zinciri vardır.
Tek değişkenli Zincir Kuralında türevleri çarpıyorduk:
Vektör değerli fonksiyonlarda aynı fikir devam eder.
Fakat sıradan sayılar yerine Jacobian matrislerini çarparız:
Burada matrislerin çarpım sırası önemlidir.
Önce \(\mathbf{x}\)'teki değişim \(\mathbf{g}\) fonksiyonundan geçerek \(\mathbf{u}\)'daki değişime dönüşür.
Ardından bu değişim \(\mathbf{f}\) fonksiyonundan geçerek \(\mathbf{y}\)'yi etkiler.
Her Jacobian, zincirdeki bir katmanın yerel değişim bilgisini taşır.
Matris çarpımı ise bu yerel etkileri birleştirerek başlangıçtan sona kadar olan toplam etkiyi verir.
Dolayısıyla tek değişkenli Zincir Kuralındaki Türevlerin Çarpımı fikri, çok boyutlu dünyada Jacobian Matrislerinin Çarpımı haline gelir.
Yapay Sinir Ağlarında Zincir Kuralı
Modern bir yapay sinir ağı çok sayıda bileşke fonksiyondan oluşur.
Basitleştirilmiş bir ağda giriş verisi önce bir doğrusal dönüşümden geçebilir:
Ardından bir aktivasyon fonksiyonu uygulanabilir:
Bu çıktı başka bir katmana gönderilebilir:
ve tekrar bir aktivasyon fonksiyonundan geçirilebilir:
Son olarak modelin tahmini gerçek değerle karşılaştırılarak bir hata veya maliyet hesaplanır:
Bütün sistemi tek bir zincir olarak yazarsak:
elde ederiz.
Modelin öğrenebilmesi için şu soruya cevap vermemiz gerekir:
\(w_1\) ağırlığında yapılacak küçük bir değişiklik toplam hatayı ne kadar değiştirir?
Yani hesaplamak istediğimiz değer:
ifadesidir.
Fakat \(w_1\), \(L\)'yi doğrudan etkilemez.
Etkisi bütün ara değişkenlerden geçerek sonuca ulaşır.
Zincir Kuralıyla:
yazarız.
Bu uzun ifade ilk bakışta karmaşık görünebilir.
Fakat aslında yaptığımız tek şey, \(w_1\)'den \(L\)'ye giden yol üzerindeki bütün yerel türevleri çarpmaktır.
Her katman yalnızca kendi yerel türevini bilmek zorundadır.
Bütün ağın duyarlılığı ise Zincir Kuralı sayesinde bu küçük bilgiler birleştirilerek hesaplanır.
Basit Bir Nöronda Zincir Kuralı
Bu fikri daha somut görmek için tek bir nöron düşünelim.
Bu konuya yapay sinir ağlarına geldiğimizde tekrar değineceğiz. Henüz nöronun ne olduğunu anlatmadığım için bu kısım biraz havada kalabilir ancak kulak dolgunluğu olması açısından işlemekte fayda var.
Nöronun doğrusal birleşimi:
çıktısı:
ve maliyet fonksiyonu:
olsun.
Amacımız ağırlığın hatayı nasıl etkilediğini bulmaktır:
Bağımlılık zincirimiz:
şeklindedir.
Zincir Kuralına göre:
Şimdi her yerel türevi ayrı ayrı hesaplayalım.
Maliyet fonksiyonu için:
Aktivasyon fonksiyonu için:
Doğrusal birleşim için:
olur.
Bunları bir araya getirdiğimizde:
sonucuna ulaşırız.
Bu türev bize ağırlığın hangi yönde ve ne kadar değiştirilmesinin hatayı etkileyeceğini söyler.
Bir yapay sinir ağının öğrenme sürecinde milyonlarca veya milyarlarca parametre için buna benzer türevler hesaplanır.
Matematiksel temel ise değişmez:
Yerel türevler hesaplanır ve Zincir Kuralıyla birbirine bağlanır.
Geri Yayılım Nedir?
Yapay sinir ağlarında Zincir Kuralının sistematik biçimde uygulanmasına geri yayılım (Backpropagation) denir.
Model önce ileri yönde bir hesaplama yapar.
Bu aşamaya ileri yayılım (Forward Pass) denir.
İleri yayılım sırasında her ara değişkenin değeri hesaplanır ve gerektiğinde daha sonra kullanılmak üzere saklanır.
Ardından hata değerinden başlanarak geriye doğru ilerlenir.
Bu aşamada her düğüm kendisine ulaşan türevi kendi yerel türeviyle çarpar ve sonucu kendisinden önceki düğümlere aktarır.
Bir düğüme birden fazla yoldan türev geliyorsa bu katkılar toplanır.
Yani geri yayılımın bütün mekanizması iki temel kurala dayanır:
Geri yayılım, Zincir Kuralından farklı yeni bir matematiksel kural değildir.
Zincir Kuralını büyük bir hesaplama grafiği üzerinde tekrar tekrar ve verimli biçimde uygulayan bir algoritmadır.
Bu sayede ağın bütün parametrelerinin hata üzerindeki etkisi tek bir geriye doğru geçişle hesaplanabilir.
Tüm bunlara, yapay sinir ağlarına geldiğimizde tekrar değineceğiz.
Kaybolan ve Patlayan Gradyanlar
Zincir Kuralında uzun bir yol üzerindeki türevlerin çarpıldığını öğrendik.
Bu çarpım çok derin ağlarda önemli bir probleme yol açabilir.
Zincir üzerindeki yerel türevlerin büyük bölümü \(1\)'den küçükse bu değerler tekrar tekrar çarpıldığında sonuç giderek küçülür.
Örneğin:
olur.
Katman sayısı arttıkça başlangıçtaki katmanlara ulaşan gradyan neredeyse sıfıra yaklaşabilir.
Buna kaybolan gradyan (Vanishing Gradient) problemi denir.
Yerel türevlerin büyük bölümü \(1\)'den büyükse bu kez çarpım hızla büyüyebilir.
Örneğin:
olur.
Bu duruma ise patlayan gradyan (Exploding Gradient) problemi denir.
Her iki problem de modelin sağlıklı biçimde öğrenmesini zorlaştırır.
Burada önemli olan, bu sorunların rastlantısal olmadığını görmektir.
Doğrudan Zincir Kuralındaki ardışık çarpım yapısından doğarlar.
Modern ağ mimarilerinde kullanılan uygun aktivasyon fonksiyonları, dikkatli ağırlık başlangıçları, normalizasyon yöntemleri ve artık bağlantılar bu etkileri azaltmaya yardımcı olur.
Bu yöntemlerin ayrıntıları ilerleyen yapay zeka makalelerimizin konusu olacak.
Zincir Kuralının Büyük Resmi
Bu makaleye basit bir soruyla başlamıştık:
Bir değişkendeki küçük değişim, kendisine bağlı başka değişkenler üzerinden geçerek nihai sonucu ne kadar değiştirir?
Tek değişkenli bir bileşke fonksiyonda cevabımız:
oldu.
Zincir uzadığında yol üzerindeki bütün yerel türevleri çarptık.
Birden fazla yol olduğunda her yol üzerindeki etkileri çarpıp farklı yolların katkılarını topladık.
Çok değişkenli fonksiyonlarda aynı fikri kısmi türevlerle ifade ettik:
Birden fazla giriş ve çıktı olduğunda bütün yerel değişimleri Jacobian matrislerinde topladık.
Vektör değerli fonksiyonların bileşkesinde ise Jacobian matrislerini çarptık.
Son olarak aynı yapının bir yapay sinir ağındaki hesaplama grafiği üzerinde geriye doğru uygulanmasının geri yayılım algoritmasını oluşturduğunu gördük.
Aslında bütün bu örneklerde tek bir fikir vardı:
Zincir Kuralı yalnızca bileşke fonksiyonların türevini almak için kullanılan bir formül değildir.
Bir sistemin parçaları arasındaki yerel ilişkilerden bütün sistemin davranışını çıkarmamızı sağlayan genel bir düşünme biçimidir.
Bu nedenle Kalkülüs ile yapay zeka arasındaki en önemli köprülerden biridir.
Sonuç
Uzun bir makale oldu, toparlasak iyi olacak. Bu makalede:
- bileşke fonksiyonların bağımlılık zincirlerini,
- tek değişkenli Zincir Kuralını,
- değişim oranlarının neden çarpıldığını,
- uzun zincirlerde yerel türevlerin nasıl birleştiğini,
- çok değişkenli Zincir Kuralını ve toplam türevi,
- hesaplama grafiklerinde farklı yolların etkilerinin nasıl toplandığını,
- Jacobian matrisini,
- yapay sinir ağlarında Zincir Kuralının nasıl kullanıldığını,
- geri yayılımın matematiksel temelini,
- kaybolan ve patlayan gradyanların neden ortaya çıktığını
inceledik.
Türev bize tek bir değişimin hızını öğretti.
Kısmi Türevler ve Gradyan çok boyutlu değişimi anlamamızı sağladı.
Zincir Kuralı ise bütün bu değişimlerin birbirine bağlı bir sistem içerisinde nasıl aktarıldığını gösterdi.
Artık bir yapay sinir ağının çıktısından başlayarak en gerideki parametreye kadar uzanan etkinin matematiksel olarak nasıl hesaplandığını biliyoruz.
Bir sonraki makalemizde matematik serimizin yeni bir bölümüne geçecek ve belirsizliği sayılarla ifade etmemizi sağlayan Temel Olasılık Kavramlarını inceleyeceğiz.
Yazar: Levent KARAGÖL
