69 puan yazan GN⁺ 2026-02-17 | 1 yorum | WhatsApp'ta paylaş
  • karpathy’nin yayımladığı bir sanat projesi. Harici bağımlılık olmadan 200 satırlık tek bir dosyada GPT’nin tüm algoritmasını uygular
  • Üretim ortamındaki LLM’lerden farkı yalnızca ölçek ve verimlilik; öz aynı. Bu kodu anlamak, GPT’nin algoritmik özünü anlamak demek
  • Veri kümesi, tokenizer, autograd motoru, GPT-2 benzeri Transformer mimarisi, Adam optimizer, eğitim ve çıkarım döngüsünün tamamını içerir
  • micrograd, makemore, nanogpt gibi önceki projelerle 10 yıllık LLM sadeleştirme çalışmalarının damıtılmış hali; artık daha fazla sadeleştirilemeyecek en küçük biçimde GPT’nin özünü taşır
  • 32.000 isim verisiyle eğitilerek inandırıcı yeni isimler üretir ve tüm hesaplamaları skaler düzeyde autograd ile doğrudan yapar
  • Eğitim süreci kayıp hesaplama → geri yayılım → Adam güncellemesi adımlarından oluşur ve yaklaşık 1 dakika içinde çalıştırılabilir

microgpt genel bakış

  • microgpt, GPT modelinin eğitim ve çıkarım sürecini eksiksiz biçimde uygulayan 200 satırlık bir Python betiğidir
    • Harici kütüphane olmadan veri kümesi, tokenizer, autograd, model, optimizer, eğitim döngüsü bileşenlerinin tümünü içerir
  • micrograd, makemore, nanogpt gibi mevcut projeleri birleştirip tek dosyada toplar
  • “Artık daha fazla sadeleştirilemez” düzeyinde, yalnızca algoritmik çekirdeği bırakan bir uygulama
  • Kodun tamamı GitHub Gist, web sayfası ve Google Colab üzerinden sunuluyor

Veri kümesi yapısı

  • Büyük dil modellerinin yakıtı metin veri akışıdır; üretim ortamında internet sayfaları kullanılırken microgpt’de satır başına bir ad içeren 32.000 isimlik basit bir örnek kullanılır
  • Her isim birer "belge" olarak ele alınır ve modelin amacı veri içindeki istatistiksel örüntüleri öğrenip benzer yeni belgeler üretmektir
  • Eğitim tamamlandığında model, "kamon", "karai", "vialan" gibi inandırıcı yeni isimler "halüsinasyon" olarak üretir
  • ChatGPT açısından bakıldığında kullanıcıyla yapılan konuşma da yalnızca "tuhaf görünümlü bir belge"dir; belge prompt ile başlatılır ve modelin yanıtı istatistiksel belge tamamlama sayılır

Tokenizer

  • Sinir ağları karakterlerle değil sayılarla çalıştığı için, metni tamsayı token ID dizilerine dönüştürmenin ve yeniden geri çevirmenin bir yolu gerekir
  • tiktoken (GPT-4 tarafından kullanılır) gibi üretim tokenizer’ları verimlilik için karakter parçaları düzeyinde çalışır; ancak en basit tokenizer, veri kümesindeki her benzersiz karaktere bir tamsayı atar
  • Küçük a-z harfleri sıralanır ve her karaktere indeks olarak bir ID verilir; tamsayı değerinin kendisi anlam taşımaz, her token ayrı bir ayrık semboldür
  • BOS(Beginning of Sequence) özel token’ı eklenerek "yeni bir belgenin başladığı/bittiği" belirtilir; böylece "emma" [BOS, e, m, m, a, BOS] olarak sarılır
  • Nihai sözlük boyutu 27’dir (26 küçük harf + 1 BOS)

Otomatik türev alma (Autograd)

  • Sinir ağı eğitimi için gradyanlar gerekir: her parametre için "bu değeri biraz artırırsam kayıp artar mı, azalır mı, ne kadar?" sorusunun yanıtını bilmek gerekir
  • Hesaplama grafiği çok sayıda girişe sahip olsa da tek bir skaler çıktı olan kayıp (loss) değerinde birleşir
  • Geri yayılım (Backpropagation) çıktıdan başlayıp grafiği ters yönde izler ve kalkülüsün zincir kuralına dayanarak tüm girişler için kaybın gradyanını hesaplar
  • Value sınıfı ile uygulanır: her Value, tek bir skaleri (.data) sarar ve nasıl hesaplandığını izler
    • Toplama, çarpma gibi işlemlerde yeni Value, girişleri (_children) ve ilgili işlemin yerel türevlerini (_local_grads) hatırlar
    • Örneğin __mul__, ∂(a·b)/∂a=b ve ∂(a·b)/∂b=a değerlerini kaydeder
  • Desteklenen işlem blokları: toplama, çarpma, üs alma, log, exp, ReLU
  • backward() metodu grafiği ters topolojik sırayla dolaşır ve her adımda zincir kuralını uygular
    • Kayıp düğümünde self.grad = 1 ile başlar (∂L/∂L=1)
    • Yerel gradyanlar yol boyunca çarpılarak parametrelere kadar yayılır
  • += ile biriktirme (atama değil): grafik dallandığında her daldan gradyan bağımsız biçimde akar ve toplanması gerekir (çok değişkenli zincir kuralının sonucu)
  • PyTorch’un .backward() yöntemiyle algoritmik olarak aynıdır; ancak tensörler yerine skaler düzeyde çalıştığı için çok daha basittir, ama verimliliği düşüktür

Parametre başlatma

  • Parametreler modelin bilgisidir; rastgele başlar ve eğitim sırasında yinelemeli olarak optimize edilen büyük bir kayan noktalı sayı kümesinden oluşur
  • Gaussian dağılımından gelen küçük rastgele değerlerle başlatılır
  • state_dict adı verilen matrislerden oluşur: embedding tablosu, attention ağırlıkları, MLP ağırlıkları, nihai çıktı projeksiyonu
  • Hiperparametre ayarları:
    • n_embd = 16: embedding boyutu
    • n_head = 4: attention head sayısı
    • n_layer = 1: katman sayısı
    • block_size = 16: maksimum dizi uzunluğu
  • Küçük model için 4.192 parametre bulunur (GPT-2’de 1,6 milyar, modern LLM’lerde yüz milyarlarca)

Mimari

  • Model mimarisi durumsuz bir fonksiyondur: tokenları, konumu, parametreleri ve önceki konumların önbelleğe alınmış anahtar/değerlerini alır, bir sonraki token için logitleri (puanları) döndürür
  • GPT-2'yi takip eder ama biraz sadeleştirilmiştir: RMSNorm (LayerNorm yerine), bias yok, ReLU (GeLU yerine)
  • Yardımcı fonksiyonlar

    • linear: matris-vektör çarpımıyla ağırlık matrisinin her satırı için bir iç çarpım hesaplar; sinir ağlarının temel yapı taşı olan öğrenilmiş doğrusal dönüşüm
    • softmax: ham puanları (logitleri) bir olasılık dağılımına dönüştürür; tüm değerler [0,1] aralığına girer ve toplamları 1 olur; sayısal kararlılık için önce maksimum değer çıkarılır
    • rmsnorm: vektörü birim karekök ortalama kare değerine sahip olacak şekilde yeniden ölçeklendirerek aktivasyonların ağ boyunca büyümesini ya da küçülmesini önler, eğitimi kararlı hale getirir
  • Model yapısı

    • Embedding: token ID'leri ve konum ID'leri, ilgili embedding tablolarındaki (wte, wpe) satırlara bakar; iki vektör toplanarak tokenın ne olduğu ve dizide nerede bulunduğu aynı anda kodlanır
      • Modern LLM'ler konum embedding'lerini atlayıp RoPE gibi göreli konumlandırma teknikleri kullanır
    • Attention bloğu: mevcut tokenı Q (query), K (key), V (value) olmak üzere üç vektöre projekte eder
      • Query: "Ne arıyorum?", key: "Ne içeriyorum?", value: "Seçilirsem ne sağlıyorum?"
      • Örnek: "emma" içinde ikinci "m" bir sonrakini tahmin ederken "yakın zamanda hangi ünlü vardı?" gibi bir query öğrenebilir; önceki "e" bu query ile iyi eşleştiği için yüksek attention ağırlığı alır
      • Key ve value'lar KV cache'e eklenir, böylece önceki konumlara başvurulabilir
      • Her attention head, query ile önbelleğe alınmış tüm key'ler arasındaki iç çarpımı (√d_head ile ölçeklenmiş) hesaplar; softmax ile attention ağırlıkları elde edilir ve önbelleğe alınmış value'ların ağırlıklı toplamı hesaplanır
      • Tüm head çıktıları birleştirilip attn_wo ile projekte edilir
      • Attention bloğu, t konumundaki tokenın geçmişteki 0..t-1 tokenlarını "görebildiği" tek yerdir; attention bir token iletişim mekanizmasıdır
    • MLP bloğu: 2 katmanlı bir feedforward ağ: embedding boyutunun 4 katına genişletme → ReLU uygulama → tekrar daraltma
      • Konum başına "düşünmenin" büyük kısmı burada gerçekleşir
      • Attention'dan farklı olarak t anında tamamen yerel bir hesaplamadır
      • Transformer, iletişim (attention) ile hesaplamayı (MLP) ardışık olarak yerleştirir
    • Residual bağlantılar: hem attention hem de MLP blokları çıktılarını yeniden girdiye ekler
      • Bu, gradyanların ağdan doğrudan geçmesini sağlayarak derin modellerin eğitilebilir olmasını sağlar
    • Çıktı: son gizli durum lm_head ile sözlük boyutuna projekte edilerek token başına bir logit üretilir (burada 27 sayı); yüksek logit = o tokenın sıradaki olma olasılığı daha yüksek
    • KV cache özelliği: eğitim sırasında KV cache kullanımı nadirdir, ancak microgpt her seferinde yalnızca bir token işlediği için açıkça oluşturulur; önbelleğe alınmış key ve value'lar, hesaplama grafiğinde geri yayılımın hedefi olan canlı Value düğümleridir

Eğitim döngüsü

  • Eğitim döngüsü tekrarlı olarak şunları yapar: (1) belge seç → (2) tokenlar üzerinde model forward çalıştır → (3) kaybı hesapla → (4) backprop ile gradyanları elde et → (5) parametreleri güncelle
  • Tokenization

    • Her eğitim adımında bir belge seçilir ve iki yanına BOS eklenir: "emma" → [BOS, e, m, m, a, BOS]
    • Modelin hedefi, önceki tokenlar verildiğinde her bir sonraki tokenı tahmin etmektir
  • Forward pass ve kayıp

    • Tokenlar modele birer birer verilirken KV cache oluşturulur
    • Her konumda model 27 logit üretir, bunlar softmax ile olasılığa dönüştürülür
    • Her konumdaki kayıp, doğru bir sonraki tokenın negatif log olasılığıdır: −log p(target); buna cross-entropy loss denir
    • Kayıp, modelin gerçekte gelecek olana ne kadar şaşırdığını ölçer: 1.0 olasılık atarsa kayıp 0, olasılık 0'a yakınsa kayıp +∞ olur
    • Belgedeki tüm konumların kaybı ortalanarak tek bir skaler kayıp elde edilir
  • Backward pass

    • loss.backward() bir kez çağrılarak tüm hesaplama grafiği üzerinde geri yayılım çalıştırılır
    • Sonrasında her parametrenin .grad değeri, kaybı azaltmak için nasıl değişmesi gerektiğini gösterir
  • Adam optimizer

    • Basit gradient descent (p.data -= lr * p.grad) yerine Adam kullanılır
    • Parametre başına iki hareketli ortalama tutulur:
      • m: son gradyanların ortalaması (momentum)
      • v: son gradyan karelerinin ortalaması (parametre başına öğrenme oranı uyarlaması)
    • m_hat, v_hat, sıfırdan başlatılan m ve v için bias düzeltmesidir
    • Öğrenme oranı eğitim boyunca doğrusal olarak azalır
    • Güncellemeden sonra .grad = 0 ile sıfırlanır
  • Eğitim sonucu

    • 1.000 adım boyunca kayıp yaklaşık 3.3'ten (27 token arasında rastgele tahmin: −log(1/27)≈3.3) yaklaşık 2.37'ye düşer
    • Daha düşük daha iyidir ve en düşük değer 0'dır (mükemmel tahmin); yani gelişme alanı olsa da modelin isimlerin istatistiksel örüntülerini öğrendiği açıktır

Çıkarım

  • Eğitim tamamlandıktan sonra modelden yeni isimler örneklenebilir; parametreler sabitlenir, forward pass döngü içinde çalıştırılır ve üretilen her token bir sonraki girdi olarak geri beslenir
  • Örnekleme süreci

    • Her örnek BOS tokenıyla başlar ("yeni isim başlat")
    • Model 27 logit üretir → olasılığa dönüştürülür → bu olasılıklara göre rastgele bir token örneklenir
    • Bu token bir sonraki girdi olarak geri beslenir; model tekrar BOS üretince ("bitti") veya maksimum dizi uzunluğuna ulaşılınca durur
  • Sıcaklık (Temperature)

    • Softmax öncesinde logitler sıcaklığa bölünür
    • Sıcaklık 1.0: modelin öğrendiği dağılımdan doğrudan örnekleme
    • Düşük sıcaklık (örn. 0.5): dağılımı keskinleştirir, modelin daha temkinli davranıp üst sıralı seçimleri yapma olasılığını artırır
    • Sıcaklık 0'a yakın: her zaman olasılığı en yüksek tek tokenı seçer (greedy decoding)
    • Yüksek sıcaklık: dağılımı düzleştirir, daha çeşitli ama daha az tutarlı çıktılar üretir

Çalıştırma yöntemi

  • Yalnızca Python gerekir (pip install yok, bağımlılık yok): python train.py
  • MacBook'ta yaklaşık 1 dakika sürer
  • Her adımda kayıp yazdırılır: ~3.3'ten (rastgele) ~2.37'ye düşer
  • Eğitim tamamlandıktan sonra halüsinasyon ürünü yeni isimler üretir: "kamon", "ann", "karai" vb.
  • Google Colab notebook'unda da çalıştırılabilir, Gemini'ye soru sorulabilir
  • Başka veri kümeleri denenebilir, num_steps artırılarak daha uzun eğitim yapılabilir, model boyutu büyütülerek daha iyi sonuçlar alınabilir

Kodun ilerleme aşamaları

Dosya Eklenen içerik
train0.py Bigram sayım tablosu — sinir ağı yok, gradyan yok
train1.py MLP + manuel gradyanlar (sayısal ve analitik) + SGD
train2.py Autograd (Value sınıfı) — manuel gradyanların yerini alır
train3.py Konum embedding'leri + tek head attention + rmsnorm + residual
train4.py Multi-head attention + layer döngüsü — tam GPT mimarisi
train5.py Adam optimizer — bu dosya train.py
  • build_microgpt.py Gist'inin Revisions bölümünde tüm sürümler ve her adım arasındaki diff görülebilir

Prodüksiyon LLM'lerle farklar

  • microgpt, GPT eğitimi ve çalıştırmanın tam algoritmik özünü içerir; ChatGPT gibi prodüksiyon LLM'lerden farkı çekirdek algoritmayı değiştirmez, bunu ölçekte çalıştıran unsurlardır
  • Veri

    • 32K kısa isim yerine trilyonlarca internet metni token'ı (web sayfaları, kitaplar, kod vb.) ile eğitilir
    • Veri tekilleştirme, kalite filtreleme ve alanlar arasında dikkatli harmanlama
  • Tokenizer

    • Tek karakter yerine BPE (Byte Pair Encoding) gibi alt sözcük tokenizer'ları kullanılır
    • Sık birlikte görülen karakter dizileri tek bir token'da birleştirilir; "the" gibi yaygın kelimeler tek token olurken nadir kelimeler parçalara ayrılır
    • ~100K token sözlüğü ile konum başına daha fazla içerik görüldüğünden çok daha verimlidir
  • Autograd

    • Saf Python'daki skaler Value nesneleri yerine tensor'lar (büyük çok boyutlu sayı dizileri) kullanılır ve saniyede milyarlarca kayan nokta işlemi yapan GPU/TPU üzerinde çalıştırılır
    • PyTorch, tensor'lar için autograd işlemini yürütür; FlashAttention gibi CUDA kernel'leri birden fazla işlemi birleştirir
    • Matematik aynıdır, sadece çok sayıda skaler paralel işlenir
  • Mimari

    • microgpt: 4.192 parametre, GPT-4 sınıfı model: yüzlerce milyar
    • Genel olarak çok benzer bir Transformer sinir ağıdır ama çok daha geniştir (embedding boyutu 10.000+) ve çok daha derindir (100+ katman)
    • Ek Lego blok türleri ve sıralama değişiklikleri:
      • RoPE (rotary positional embedding) — öğrenilmiş positional embedding yerine
      • GQA (grouped query attention) — KV cache boyutunu azaltır
      • Gated linear activation — ReLU yerine
      • MoE (mixture of experts) katmanları
    • Residual stream üzerinde attention (iletişim) ile MLP'nin (hesaplama) dönüşümlü olduğu çekirdek yapı büyük ölçüde korunur
  • Eğitim

    • Her adımda tek bir belge yerine büyük batch'ler (adım başına milyonlarca token), gradient accumulation, mixed precision (float16/bfloat16) ve dikkatli hyperparameter ayarı kullanılır
    • Frontier model eğitimi için binlerce GPU aylar boyunca çalıştırılır
  • Optimizasyon

    • microgpt: Adam + basit doğrusal öğrenme oranı azaltımı
    • Büyük ölçekte optimizasyon başlı başına ayrı bir alandır: düşürülmüş hassasiyet (bfloat16, fp8), büyük GPU kümelerinde eğitim
    • Optimizer ayarlarının (öğrenme oranı, weight decay, beta parametreleri, warmup/decay schedule) hassas biçimde ayarlanması gerekir; doğru değerler model boyutuna, batch boyutuna ve veri kümesi bileşimine göre değişir
    • Scaling laws (ör. Chinchilla), sabit hesaplama bütçesinin model boyutu ile eğitim token sayısı arasında nasıl dağıtılacağını yönlendirir
    • Büyük ölçekte bu ayrıntıları yanlış yapmak milyonlarca dolarlık hesaplama israfına yol açabilir; ekipler tam eğitim çalıştırmasından önce kapsamlı küçük ölçekli deneyler yapar
  • Sonraki eğitim (Post-training)

    • Eğitimden çıkan temel model ("ön eğitimli" model) bir belge tamamlayıcıdır, chatbot değildir
    • Onu ChatGPT'ye dönüştürme süreci iki adımdır:
      • SFT (supervised fine-tuning): belgeler, küratörlüğü yapılmış diyaloglarla değiştirilir ve eğitim sürdürülür; algoritmik olarak bir değişiklik yoktur
      • RL (reinforcement learning): model yanıt üretir → puan verilir (insan, "hakem" model, algoritma) → geri bildirimle öğrenir
    • Temelde hâlâ belgeler üzerinde eğitilir, ancak artık belge modelin kendisinden çıkan token'lar ile oluşur
  • Çıkarım

    • Modeli milyonlarca kullanıcıya sunmak için ayrı bir mühendislik yığını gerekir: istek batch'leme, KV cache yönetimi ve paging (vLLM vb.), hız için speculative decoding, bellek azaltımı için quantization (int8/int4 ile çalıştırma), modeli birden fazla GPU'ya dağıtma
    • Temelde hâlâ dizideki bir sonraki token'ı tahmin eder ama onu daha hızlı hâle getiren mühendisliğe büyük emek harcanır

SSS

  • Model bir şeyi "anlıyor" mu?

    • Bu felsefi bir soru olabilir ama mekanik olarak bakarsak: ortada sihirli bir şey yok
    • Model, giriş token'larını bir sonraki token için bir olasılık dağılımına eşleyen büyük bir matematik fonksiyonudur
    • Eğitim sırasında parametreler, doğru sonraki token'ı daha olası kılacak şekilde ayarlanır
    • Buna "anlama" denip denmeyeceği kişiye kalmıştır ama mekanizma tamamen bu 200 satırın içindedir
  • Neden çalışıyor?

    • Modelde binlerce ayarlanabilir parametre vardır ve optimizer her adımda kaybı düşürecek şekilde bunları biraz hareket ettirir
    • Çok sayıda adım boyunca parametreler, verinin istatistiksel düzenliliklerini yakalayan değerlere oturur
    • İsimler için örneğin: çoğu ünsüzle başlar, "qu" birlikte görünme eğilimindedir, art arda üç ünsüz nadirdir vb.
    • Model, açık kurallar değil bunları yansıtan olasılık dağılımlarını öğrenir
  • ChatGPT ile nasıl bir ilişkisi var?

    • ChatGPT, bu aynı çekirdek döngüyü (sonraki token tahmini, örnekleme, tekrar) muazzam ölçekte genişletir ve buna diyaloğa uygun sonraki eğitim ekler
    • Sohbet ederken sistem prompt'u, kullanıcı mesajı ve yanıtın hepsi sadece bir dizinin token'larıdır
    • Model, microgpt'nin isim tamamlamasıyla aynı şekilde, bir belgeyi her seferinde bir token üreterek tamamlar
  • "Halüsinasyon" nedir?

    • Model, token'ları bir olasılık dağılımından örnekleyerek üretir
    • Doğruluk kavramına sahip değildir; sadece eğitim verisine göre istatistiksel olarak makul görünen dizileri bilir
    • microgpt'nin "karia" gibi bir ismi "halüsinasyonla" üretmesi, ChatGPT'nin yanlış bir olguyu kendinden emin biçimde söylemesiyle aynı olgudur
    • Her ikisi de gerçek olmak zorunda olmayan, sadece makul görünen tamamlamalardır
  • Neden bu kadar yavaş?

    • microgpt saf Python'da aynı anda yalnızca bir skaler işler; tek bir eğitim adımı birkaç saniye sürer
    • GPU'da aynı matematik milyonlarca skaleri paralel işler ve birkaç büyüklük mertebesi daha hızlı çalışır
  • Daha iyi isimler üretmesini sağlayabilir miyim?

    • Evet: daha uzun eğitin (num_steps artırın), model boyutunu büyütün (n_embd, n_layer, n_head), daha büyük bir veri kümesi kullanın
    • Bunlar büyük ölçekte de önemli olan aynı kontrol düğmeleridir
  • Veri kümesini değiştirirsem ne olur?

    • Model, veride bulunan her türlü deseni öğrenir
    • Bunu şehir isimleri, Pokémon isimleri, İngilizce kelimeler veya kısa şiir dosyalarıyla değiştirirseniz bu kez onları üretmeyi öğrenir
    • Kodun geri kalanını değiştirmeniz gerekmez

1 yorum

 
mhj5730 2026-02-19

Güzel yazı için teşekkürler.