<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" ><generator uri="https://jekyllrb.com/" version="4.4.1">Jekyll</generator><link href="https://program.sonsuz.us/feed.xml" rel="self" type="application/atom+xml" /><link href="https://program.sonsuz.us/" rel="alternate" type="text/html" /><updated>2026-10-18T18:05:49+00:00</updated><id>https://program.sonsuz.us/feed.xml</id><title type="html">SonsuzUs</title><subtitle>Programlama ve Yazılım</subtitle><author><name>Sonsuz Us</name></author><entry><title type="html">C++ Fonksiyon Aşırı Yükleme: Tek İsim, Birden Fazla Yetenek</title><link href="https://program.sonsuz.us/posts/c-fonksiyon-asiri-yukleme-tek-isim-birden-fazla-yetenek/" rel="alternate" type="text/html" title="C++ Fonksiyon Aşırı Yükleme: Tek İsim, Birden Fazla Yetenek" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/c-fonksiyon-asiri-yukleme-tek-isim-birden-fazla-yetenek</id><content type="html" xml:base="https://program.sonsuz.us/posts/c-fonksiyon-asiri-yukleme-tek-isim-birden-fazla-yetenek/"><![CDATA[<p>Bir hesap makinesindeki “topla” düğmesinin tam sayılar, ondalıklı sayılar ve hatta metinler için farklı davranabildiğini düşünün. C++ fonksiyon aşırı yükleme sayesinde benzer işlemleri yapan fonksiyonlara aynı ismi verebilir, kullanım sırasında hangi sürümün çalışacağını derleyiciye bırakabiliriz. Böylece <code class="language-plaintext highlighter-rouge">toplaTamSayilari</code>, <code class="language-plaintext highlighter-rouge">toplaOndalikliSayilari</code> gibi isimler üretmek yerine daha sade ve anlaşılır bir arayüz oluştururuz.</p>

<p>``</p>

<h2 id="fonksiyon-aşırı-yükleme-nedir">Fonksiyon aşırı yükleme nedir?</h2>

<p>Function overloading, aynı kapsam içerisinde aynı isimli fakat farklı parametre listelerine sahip birden fazla fonksiyon tanımlamaktır. Parametre listesindeki tür, sayı veya sıralama değiştiğinde yeni bir overload meydana gelir.</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="cp">#include</span> <span class="cpf">&lt;iostream&gt;</span><span class="cp">
#include</span> <span class="cpf">&lt;string&gt;</span><span class="cp">
</span>
<span class="kt">int</span> <span class="nf">topla</span><span class="p">(</span><span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="kt">int</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span>
    <span class="k">return</span> <span class="n">a</span> <span class="o">+</span> <span class="n">b</span><span class="p">;</span>
<span class="p">}</span>

<span class="kt">double</span> <span class="nf">topla</span><span class="p">(</span><span class="kt">double</span> <span class="n">a</span><span class="p">,</span> <span class="kt">double</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span>
    <span class="k">return</span> <span class="n">a</span> <span class="o">+</span> <span class="n">b</span><span class="p">;</span>
<span class="p">}</span>

<span class="n">std</span><span class="o">::</span><span class="n">string</span> <span class="nf">topla</span><span class="p">(</span><span class="k">const</span> <span class="n">std</span><span class="o">::</span><span class="n">string</span><span class="o">&amp;</span> <span class="n">a</span><span class="p">,</span> <span class="k">const</span> <span class="n">std</span><span class="o">::</span><span class="n">string</span><span class="o">&amp;</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span>
    <span class="k">return</span> <span class="n">a</span> <span class="o">+</span> <span class="n">b</span><span class="p">;</span>
<span class="p">}</span>

<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">topla</span><span class="p">(</span><span class="mi">4</span><span class="p">,</span> <span class="mi">7</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="sc">'\n'</span><span class="p">;</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">topla</span><span class="p">(</span><span class="mf">2.5</span><span class="p">,</span> <span class="mf">1.8</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="sc">'\n'</span><span class="p">;</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">topla</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">string</span><span class="p">(</span><span class="s">"Merhaba "</span><span class="p">),</span> <span class="n">std</span><span class="o">::</span><span class="n">string</span><span class="p">(</span><span class="s">"C++"</span><span class="p">));</span>
<span class="p">}</span>
</code></pre></div></div>

<p>Burada <code class="language-plaintext highlighter-rouge">topla(4, 7)</code> çağrısı <code class="language-plaintext highlighter-rouge">int</code> sürümünü, ondalıklı argümanlar <code class="language-plaintext highlighter-rouge">double</code> sürümünü seçer. Son sürüm ise iki metni birleştirir. <code class="language-plaintext highlighter-rouge">const std::string&amp;</code> kullanılması, metinlerin gereksiz yere kopyalanmasını önler.</p>

<h2 id="derleyici-doğru-fonksiyonu-nasıl-seçer">Derleyici doğru fonksiyonu nasıl seçer?</h2>

<p>Derleyici, çağrıdaki argümanları mevcut adayların parametreleriyle karşılaştırır. Bu sürece <strong>overload resolution</strong> denir. Basitleştirilmiş biçimde her aday için bir dönüşüm maliyeti düşünülebilir:</p>

\[S = C_1 + C_2 + \cdots + C_n\]

<p>Burada $C_i$, ilgili argümanın parametre türüne dönüştürülme maliyetidir. En düşük $S$ değerine sahip aday seçilir. Tam eşleşme genellikle standart tür dönüşümünden, standart dönüşüm de kullanıcı tanımlı dönüşümden daha güçlüdür.</p>

<table>
  <thead>
    <tr>
      <th>Eşleşme türü</th>
      <th>Örnek</th>
      <th>Tercih düzeyi</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Tam eşleşme</td>
      <td><code class="language-plaintext highlighter-rouge">int</code> → <code class="language-plaintext highlighter-rouge">int</code></td>
      <td>En yüksek</td>
    </tr>
    <tr>
      <td>Terfi</td>
      <td><code class="language-plaintext highlighter-rouge">char</code> → <code class="language-plaintext highlighter-rouge">int</code></td>
      <td>Yüksek</td>
    </tr>
    <tr>
      <td>Standart dönüşüm</td>
      <td><code class="language-plaintext highlighter-rouge">int</code> → <code class="language-plaintext highlighter-rouge">double</code></td>
      <td>Orta</td>
    </tr>
    <tr>
      <td>Kullanıcı tanımlı dönüşüm</td>
      <td>Sınıf dönüşümü</td>
      <td>Daha düşük</td>
    </tr>
  </tbody>
</table>

<p><img src="/img/c-fonksiyon-asiri-87.svg" alt="c-fonksiyon-asiri-87" /></p>

<h2 id="neler-overload-oluşturur">Neler overload oluşturur?</h2>

<p>Aşağıdaki fonksiyonlar geçerli biçimde aşırı yüklenebilir:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">void</span> <span class="nf">yazdir</span><span class="p">(</span><span class="kt">int</span> <span class="n">deger</span><span class="p">);</span>
<span class="kt">void</span> <span class="nf">yazdir</span><span class="p">(</span><span class="kt">double</span> <span class="n">deger</span><span class="p">);</span>
<span class="kt">void</span> <span class="nf">yazdir</span><span class="p">(</span><span class="kt">int</span> <span class="n">deger</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tekrar</span><span class="p">);</span>
<span class="kt">void</span> <span class="nf">yazdir</span><span class="p">(</span><span class="k">const</span> <span class="n">std</span><span class="o">::</span><span class="n">string</span><span class="o">&amp;</span> <span class="n">metin</span><span class="p">);</span>
</code></pre></div></div>

<p>Birincisi ve ikincisi parametre türüyle, üçüncüsü parametre sayısıyla ayrılır. Ancak yalnızca dönüş türünü değiştirmek yeterli değildir:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">int</span> <span class="nf">hesapla</span><span class="p">(</span><span class="kt">int</span> <span class="n">x</span><span class="p">);</span>
<span class="c1">// double hesapla(int x); // Hata: Parametre listesi aynı!</span>
</code></pre></div></div>

<p>Çağıran kod yalnızca <code class="language-plaintext highlighter-rouge">hesapla(5)</code> yazdığında hangi dönüş türünü istediğini derleyici kesin olarak anlayamaz. Bu nedenle dönüş türü, fonksiyon aşırı yükleme imzasının ayırt edici parçası değildir.</p>

<h2 id="belirsizlik-tuzağı">Belirsizlik tuzağı</h2>

<p>Dönüşümler eşit derecede uygun olduğunda derleyici seçim yapamaz:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">void</span> <span class="nf">goster</span><span class="p">(</span><span class="kt">long</span> <span class="n">deger</span><span class="p">)</span> <span class="p">{}</span>
<span class="kt">void</span> <span class="nf">goster</span><span class="p">(</span><span class="kt">double</span> <span class="n">deger</span><span class="p">)</span> <span class="p">{}</span>

<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
    <span class="c1">// goster(10); // Belirsiz çağrı</span>
    <span class="n">goster</span><span class="p">(</span><span class="mi">10L</span><span class="p">);</span>   <span class="c1">// long sürümü</span>
    <span class="n">goster</span><span class="p">(</span><span class="mf">10.0</span><span class="p">);</span>  <span class="c1">// double sürümü</span>
<span class="p">}</span>
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">10</code>, <code class="language-plaintext highlighter-rouge">int</code> türündedir ve hem <code class="language-plaintext highlighter-rouge">long</code> hem de <code class="language-plaintext highlighter-rouge">double</code> türüne dönüştürülebilir. <code class="language-plaintext highlighter-rouge">L</code> ve <code class="language-plaintext highlighter-rouge">.0</code> ekleriyle niyet açıkça belirtilir. Benzer sorunlar varsayılan parametrelerle de oluşabilir.</p>

<table>
  <thead>
    <tr>
      <th>Yaklaşım</th>
      <th>Avantaj</th>
      <th>Risk</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Farklı fonksiyon adları</td>
      <td>Seçim tamamen açıktır</td>
      <td>Gereksiz isim kalabalığı</td>
    </tr>
    <tr>
      <td>Overloading</td>
      <td>Temiz ve doğal API</td>
      <td>Belirsiz çağrı ihtimali</td>
    </tr>
    <tr>
      <td>Şablonlar</td>
      <td>Çok sayıda türü destekler</td>
      <td>Hata mesajları karmaşıklaşabilir</td>
    </tr>
  </tbody>
</table>

<h2 id="ne-zaman-kullanmalıyız">Ne zaman kullanmalıyız?</h2>

<p>Aşırı yüklenen fonksiyonlar kavramsal olarak aynı işi yapmalıdır. <code class="language-plaintext highlighter-rouge">yazdir</code>, <code class="language-plaintext highlighter-rouge">hesapla</code> veya <code class="language-plaintext highlighter-rouge">ekle</code> gibi işlemler bunun için uygundur. Bir overload dosya silerken diğeri matematiksel hesap yapıyorsa ortak isim geliştiriciyi şaşırtır.</p>

<p>Kısacası function overloading, C++ arayüzlerini esnek ve okunabilir hâle getirir. Parametre listelerini belirgin tuttuğunuz, örtük dönüşümleri sınırladığınız ve her sürüme aynı kavramsal sorumluluğu verdiğiniz sürece tek bir isim gerçekten birçok yeteneği zarifçe taşıyabilir.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="c++" /><category term="fonksiyonlar" /><category term="function-overloading" /><category term="oop" /><category term="programlama" /><summary type="html"><![CDATA[Bir hesap makinesindeki “topla” düğmesinin tam sayılar, ondalıklı sayılar ve hatta metinler için farklı davranabildiğini düşünün. C++ fonksiyon aşırı yükleme sayesinde benzer işlemleri yapan fonksiyonlara aynı ismi verebilir, kullanım sırasında hangi sürümün çalışacağını derleyiciye bırakabiliriz. Böylece toplaTamSayilari, toplaOndalikliSayilari gibi isimler üretmek yerine daha sade ve anlaşılır bir arayüz oluştururuz.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/c-fonksiyon-asiri-87.png" /><media:content medium="image" url="https://program.sonsuz.us/img/c-fonksiyon-asiri-87.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">C++ İstisna Yönetimi: Hataları Güvenle Yakalamak</title><link href="https://program.sonsuz.us/posts/c-istisna-yonetimi-hatalari-guvenle-yakalamak/" rel="alternate" type="text/html" title="C++ İstisna Yönetimi: Hataları Güvenle Yakalamak" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/c-istisna-yonetimi-hatalari-guvenle-yakalamak</id><content type="html" xml:base="https://program.sonsuz.us/posts/c-istisna-yonetimi-hatalari-guvenle-yakalamak/"><![CDATA[<p>Bir C++ programı derlenmiş olsa bile çalışma sırasında dosya bulunamaması, belleğin ayrılamaması veya geçersiz veriyle karşılaşılması gibi sorunlar yaşayabilir. İstisna yönetimi, bu beklenmedik durumları programı aniden sonlandırmadan uygun bir noktaya bildirmemizi sağlar. Kısacası <code class="language-plaintext highlighter-rouge">throw</code> alarmı çalıştırır, <code class="language-plaintext highlighter-rouge">try</code> riskli bölgeyi gözetler, <code class="language-plaintext highlighter-rouge">catch</code> ise olaya müdahale eder.
``</p>
<h2 id="i̇stisna-yönetiminin-temel-mantığı">İstisna yönetiminin temel mantığı</h2>

<p>Normal koşullarda fonksiyonlar sonuçlarını <code class="language-plaintext highlighter-rouge">return</code> ile döndürür. Ancak bir fonksiyon görevini tamamlayamıyorsa sıradan bir sonuç döndürmek yanıltıcı olabilir. Örneğin pozitif sayı bekleyen bir karekök fonksiyonuna negatif değer verilmesi ayrı bir kontrol akışı gerektirir.</p>

<p>İstisna oluştuğunda program, uygun bir <code class="language-plaintext highlighter-rouge">catch</code> bloğu bulana kadar çağrı zincirinde geriye ilerler. Bu sürece <strong>stack unwinding</strong> denir. Matematiksel olarak bir fonksiyonun geçerli kümesini şöyle gösterebiliriz:</p>

\[f(x) = \sqrt{x}, \qquad x \in [0, \infty)\]

<p>Burada $x &lt; 0$ olması, fonksiyon sözleşmesinin ihlal edildiğini belirtir.</p>

<table>
  <thead>
    <tr>
      <th>Araç</th>
      <th>Görevi</th>
      <th>Benzetme</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">try</code></td>
      <td>Hata oluşturabilecek kodu çalıştırır</td>
      <td>Güvenlik kamerası</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">throw</code></td>
      <td>İstisna üretir</td>
      <td>Alarm düğmesi</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">catch</code></td>
      <td>Belirli istisnayı yakalar</td>
      <td>Müdahale ekibi</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">noexcept</code></td>
      <td>Fonksiyonun istisna fırlatmayacağını bildirir</td>
      <td>Güvenlik garantisi</td>
    </tr>
  </tbody>
</table>

<h2 id="temel-try-throw-ve-catch-kullanımı">Temel <code class="language-plaintext highlighter-rouge">try</code>, <code class="language-plaintext highlighter-rouge">throw</code> ve <code class="language-plaintext highlighter-rouge">catch</code> kullanımı</h2>

<p>Aşağıdaki örnek, bölme işleminden önce paydayı denetler. Sıfıra bölme tespit edildiğinde <code class="language-plaintext highlighter-rouge">std::runtime_error</code> nesnesi fırlatılır:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="cp">#include</span> <span class="cpf">&lt;iostream&gt;</span><span class="cp">
#include</span> <span class="cpf">&lt;stdexcept&gt;</span><span class="cp">
</span>
<span class="kt">double</span> <span class="nf">bol</span><span class="p">(</span><span class="kt">double</span> <span class="n">pay</span><span class="p">,</span> <span class="kt">double</span> <span class="n">payda</span><span class="p">)</span> <span class="p">{</span>
    <span class="k">if</span> <span class="p">(</span><span class="n">payda</span> <span class="o">==</span> <span class="mf">0.0</span><span class="p">)</span> <span class="p">{</span>
        <span class="k">throw</span> <span class="n">std</span><span class="o">::</span><span class="n">runtime_error</span><span class="p">(</span><span class="s">"Sıfıra bölme girişimi!"</span><span class="p">);</span>
    <span class="p">}</span>
    <span class="k">return</span> <span class="n">pay</span> <span class="o">/</span> <span class="n">payda</span><span class="p">;</span>
<span class="p">}</span>

<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
    <span class="k">try</span> <span class="p">{</span>
        <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">bol</span><span class="p">(</span><span class="mi">42</span><span class="p">,</span> <span class="mi">0</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="sc">'\n'</span><span class="p">;</span>
    <span class="p">}</span> <span class="k">catch</span> <span class="p">(</span><span class="k">const</span> <span class="n">std</span><span class="o">::</span><span class="n">runtime_error</span><span class="o">&amp;</span> <span class="n">hata</span><span class="p">)</span> <span class="p">{</span>
        <span class="n">std</span><span class="o">::</span><span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">"Hata: "</span> <span class="o">&lt;&lt;</span> <span class="n">hata</span><span class="p">.</span><span class="n">what</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="sc">'\n'</span><span class="p">;</span>
    <span class="p">}</span>
<span class="p">}</span>
</code></pre></div></div>

<p>İstisnanın <code class="language-plaintext highlighter-rouge">const</code> referansla yakalanması gereksiz kopyalamayı engeller ve çok biçimliliği korur. <code class="language-plaintext highlighter-rouge">what()</code> metodu ise hatanın açıklamasını verir. Program kontrolsüz biçimde çökmek yerine kullanıcıya anlamlı bir mesaj sunar.</p>

<h2 id="standart-mı-özel-istisna-mı">Standart mı, özel istisna mı?</h2>

<p>C++ standart kütüphanesi <code class="language-plaintext highlighter-rouge">std::exception</code> tabanlı birçok hata türü sağlar.</p>

<table>
  <thead>
    <tr>
      <th>İstisna</th>
      <th>Uygun kullanım</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">std::invalid_argument</code></td>
      <td>Geçersiz fonksiyon argümanı</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">std::out_of_range</code></td>
      <td>Aralık dışı indeks</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">std::runtime_error</code></td>
      <td>Genel çalışma zamanı sorunu</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">std::bad_alloc</code></td>
      <td>Bellek ayırma başarısızlığı</td>
    </tr>
  </tbody>
</table>

<p>Uygulamaya özgü hatalar için özel bir sınıf da tanımlanabilir:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="cp">#include</span> <span class="cpf">&lt;stdexcept&gt;</span><span class="cp">
#include</span> <span class="cpf">&lt;string&gt;</span><span class="cp">
</span>
<span class="k">class</span> <span class="nc">BakiyeHatasi</span> <span class="o">:</span> <span class="k">public</span> <span class="n">std</span><span class="o">::</span><span class="n">runtime_error</span> <span class="p">{</span>
<span class="nl">public:</span>
    <span class="k">explicit</span> <span class="n">BakiyeHatasi</span><span class="p">(</span><span class="k">const</span> <span class="n">std</span><span class="o">::</span><span class="n">string</span><span class="o">&amp;</span> <span class="n">mesaj</span><span class="p">)</span>
        <span class="o">:</span> <span class="n">std</span><span class="o">::</span><span class="n">runtime_error</span><span class="p">(</span><span class="n">mesaj</span><span class="p">)</span> <span class="p">{}</span>
<span class="p">};</span>

<span class="kt">void</span> <span class="nf">paraCek</span><span class="p">(</span><span class="kt">double</span> <span class="n">bakiye</span><span class="p">,</span> <span class="kt">double</span> <span class="n">miktar</span><span class="p">)</span> <span class="p">{</span>
    <span class="k">if</span> <span class="p">(</span><span class="n">miktar</span> <span class="o">&gt;</span> <span class="n">bakiye</span><span class="p">)</span> <span class="p">{</span>
        <span class="k">throw</span> <span class="n">BakiyeHatasi</span><span class="p">(</span><span class="s">"Yetersiz bakiye"</span><span class="p">);</span>
    <span class="p">}</span>
<span class="p">}</span>
</code></pre></div></div>

<p>Bu yaklaşım, çağıran kodun banka işlemlerine özgü problemi diğer çalışma zamanı hatalarından ayırmasını sağlar.</p>

<h2 id="yakalama-sırası-ve-yeniden-fırlatma">Yakalama sırası ve yeniden fırlatma</h2>

<p><code class="language-plaintext highlighter-rouge">catch</code> blokları özel türden genel türe doğru sıralanmalıdır. Aksi hâlde <code class="language-plaintext highlighter-rouge">std::exception</code> gibi genel bir blok, türetilmiş bütün istisnaları önce yakalayabilir.</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">try</span> <span class="p">{</span>
    <span class="n">paraCek</span><span class="p">(</span><span class="mi">100</span><span class="p">,</span> <span class="mi">250</span><span class="p">);</span>
<span class="p">}</span> <span class="k">catch</span> <span class="p">(</span><span class="k">const</span> <span class="n">BakiyeHatasi</span><span class="o">&amp;</span> <span class="n">hata</span><span class="p">)</span> <span class="p">{</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="n">hata</span><span class="p">.</span><span class="n">what</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="sc">'\n'</span><span class="p">;</span>
    <span class="k">throw</span><span class="p">;</span> <span class="c1">// Aynı istisnayı üst seviyeye iletir</span>
<span class="p">}</span> <span class="k">catch</span> <span class="p">(</span><span class="k">const</span> <span class="n">std</span><span class="o">::</span><span class="n">exception</span><span class="o">&amp;</span> <span class="n">hata</span><span class="p">)</span> <span class="p">{</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">"Genel hata: "</span> <span class="o">&lt;&lt;</span> <span class="n">hata</span><span class="p">.</span><span class="n">what</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="sc">'\n'</span><span class="p">;</span>
<span class="p">}</span>
</code></pre></div></div>

<p>Parametresiz <code class="language-plaintext highlighter-rouge">throw;</code>, mevcut istisnayı türünü kaybetmeden yeniden fırlatır. Bu yöntem, alt seviyede kayıt tutup üst seviyede kullanıcıya cevap vermek için kullanışlıdır.</p>

<h2 id="güvenli-tasarım-için-kısa-kurallar">Güvenli tasarım için kısa kurallar</h2>

<p>İstisnaları sıradan döngü kontrolü amacıyla değil, gerçekten olağan dışı durumlar için kullanın. Kaynak yönetiminde RAII yaklaşımını tercih edin; <code class="language-plaintext highlighter-rouge">std::vector</code>, <code class="language-plaintext highlighter-rouge">std::string</code> ve akıllı işaretçiler stack unwinding sırasında otomatik olarak temizlenir. Yıkıcılar mümkünse istisna fırlatmamalıdır. Ayrıca yalnızca gerçekten garanti verebildiğiniz fonksiyonları <code class="language-plaintext highlighter-rouge">noexcept</code> olarak işaretleyin.</p>

<p>Doğru tasarlanmış istisna yönetimi hataları yok etmez; onları görünür, sınıflandırılabilir ve güvenli biçimde yönetilebilir hâle getirir. Böylece programınız ilk beklenmedik durumda havlu atmak yerine kontrollü bir iniş yapar.</p>

<p><img src="/img/c-istisna-yonetimi-33.svg" alt="c-istisna-yonetimi-33" /></p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="c++" /><category term="istisna yönetimi" /><category term="exception handling" /><category term="try-catch" /><category term="hata yönetimi" /><summary type="html"><![CDATA[Bir C++ programı derlenmiş olsa bile çalışma sırasında dosya bulunamaması, belleğin ayrılamaması veya geçersiz veriyle karşılaşılması gibi sorunlar yaşayabilir. İstisna yönetimi, bu beklenmedik durumları programı aniden sonlandırmadan uygun bir noktaya bildirmemizi sağlar. Kısacası throw alarmı çalıştırır, try riskli bölgeyi gözetler, catch ise olaya müdahale eder.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/c-istisna-yonetimi-33.png" /><media:content medium="image" url="https://program.sonsuz.us/img/c-istisna-yonetimi-33.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">C# Operatörler ve Program Kontrolü: Kararlardan Döngülere</title><link href="https://program.sonsuz.us/posts/c-operatorler-ve-program-kontrolu-kararlardan-dongulere/" rel="alternate" type="text/html" title="C# Operatörler ve Program Kontrolü: Kararlardan Döngülere" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/c-operatorler-ve-program-kontrolu-kararlardan-dongulere</id><content type="html" xml:base="https://program.sonsuz.us/posts/c-operatorler-ve-program-kontrolu-kararlardan-dongulere/"><![CDATA[<p>Bir C# programı yalnızca yukarıdan aşağıya çalışan komutlardan oluşmaz. Değerleri karşılaştırır, koşullara göre karar verir ve gerektiğinde aynı işlemi tekrarlar. Operatörler bu kararların kelimeleri, kontrol blokları ise programın trafik ışıklarıdır. Gelin C# kodunun nasıl düşündüğünü adım adım inceleyelim.</p>

<p>``</p>

<h2 id="operatörlerin-temel-mantığı">Operatörlerin temel mantığı</h2>

<p>Operatör, bir veya daha fazla değer üzerinde işlem yapan semboldür. Örneğin <code class="language-plaintext highlighter-rouge">+</code> iki sayıyı toplarken <code class="language-plaintext highlighter-rouge">&gt;=</code> değerleri karşılaştırır. <code class="language-plaintext highlighter-rouge">=</code> ile <code class="language-plaintext highlighter-rouge">==</code> arasındaki fark özellikle önemlidir: İlki atama, ikincisi eşitlik kontrolüdür.</p>

<div class="language-csharp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">int</span> <span class="n">puan</span> <span class="p">=</span> <span class="m">75</span><span class="p">;</span>              <span class="c1">// Atama</span>
<span class="kt">bool</span> <span class="n">gectiMi</span> <span class="p">=</span> <span class="n">puan</span> <span class="p">&gt;=</span> <span class="m">50</span><span class="p">;</span>  <span class="c1">// Karşılaştırma</span>
<span class="kt">int</span> <span class="n">bonusluPuan</span> <span class="p">=</span> <span class="n">puan</span> <span class="p">+</span> <span class="m">10</span><span class="p">;</span>
</code></pre></div></div>

<p>Aritmetik operatörler matematiksel işlemleri gerçekleştirir. İki sayı $a$ ve $b$ olmak üzere kalan işlemi $a \bmod b$ biçiminde düşünülebilir. C# dilinde bunun karşılığı <code class="language-plaintext highlighter-rouge">%</code> operatörüdür.</p>

<table>
  <thead>
    <tr>
      <th>Grup</th>
      <th>Operatörler</th>
      <th>Örnek kullanım</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Aritmetik</td>
      <td><code class="language-plaintext highlighter-rouge">+</code>, <code class="language-plaintext highlighter-rouge">-</code>, <code class="language-plaintext highlighter-rouge">*</code>, <code class="language-plaintext highlighter-rouge">/</code>, <code class="language-plaintext highlighter-rouge">%</code></td>
      <td><code class="language-plaintext highlighter-rouge">sayi % 2</code></td>
    </tr>
    <tr>
      <td>Karşılaştırma</td>
      <td><code class="language-plaintext highlighter-rouge">==</code>, <code class="language-plaintext highlighter-rouge">!=</code>, <code class="language-plaintext highlighter-rouge">&lt;</code>, <code class="language-plaintext highlighter-rouge">&gt;</code>, <code class="language-plaintext highlighter-rouge">&lt;=</code>, <code class="language-plaintext highlighter-rouge">&gt;=</code></td>
      <td><code class="language-plaintext highlighter-rouge">yas &gt;= 18</code></td>
    </tr>
    <tr>
      <td>Mantıksal</td>
      <td><code class="language-plaintext highlighter-rouge">&amp;&amp;</code>, <code class="language-plaintext highlighter-rouge">||</code>, <code class="language-plaintext highlighter-rouge">!</code></td>
      <td><code class="language-plaintext highlighter-rouge">aktif &amp;&amp; yetkili</code></td>
    </tr>
    <tr>
      <td>Atama</td>
      <td><code class="language-plaintext highlighter-rouge">=</code>, <code class="language-plaintext highlighter-rouge">+=</code>, <code class="language-plaintext highlighter-rouge">-=</code>, <code class="language-plaintext highlighter-rouge">*=</code>, <code class="language-plaintext highlighter-rouge">/=</code></td>
      <td><code class="language-plaintext highlighter-rouge">puan += 5</code></td>
    </tr>
    <tr>
      <td>Artırma/Azaltma</td>
      <td><code class="language-plaintext highlighter-rouge">++</code>, <code class="language-plaintext highlighter-rouge">--</code></td>
      <td><code class="language-plaintext highlighter-rouge">sayac++</code></td>
    </tr>
  </tbody>
</table>

<p><img src="/img/c-operatorler-ve-81.svg" alt="c-operatorler-ve-81" /></p>

<p>Mantıksal operatörler Boolean cebirine dayanır. <code class="language-plaintext highlighter-rouge">&amp;&amp;</code> için sonuç yalnızca iki ifade de doğruysa doğrudur:</p>

\[A \land B = true \quad \text{yalnızca A ve B doğruysa}\]

<p><code class="language-plaintext highlighter-rouge">||</code> operatöründe ise koşullardan birinin doğru olması yeterlidir. C# kısa devre değerlendirmesi uygular; <code class="language-plaintext highlighter-rouge">A &amp;&amp; B</code> ifadesinde <code class="language-plaintext highlighter-rouge">A</code> yanlışsa <code class="language-plaintext highlighter-rouge">B</code> çalıştırılmaz. Bu davranış hem performans sağlar hem de bazı null hatalarını engeller.</p>

<h2 id="ca-özgü-kullanışlı-işleçler">C#’a özgü kullanışlı işleçler</h2>

<p>C#, null değerlerle güvenli çalışmayı kolaylaştıran operatörler sunar. <code class="language-plaintext highlighter-rouge">?.</code> yalnızca nesne null değilse üyeye erişir; <code class="language-plaintext highlighter-rouge">??</code> ise sol taraf null olduğunda yedek değer üretir.</p>

<div class="language-csharp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">string</span><span class="p">?</span> <span class="n">kullaniciAdi</span> <span class="p">=</span> <span class="k">null</span><span class="p">;</span>
<span class="kt">int</span><span class="p">?</span> <span class="n">uzunluk</span> <span class="p">=</span> <span class="n">kullaniciAdi</span><span class="p">?.</span><span class="n">Length</span><span class="p">;</span>
<span class="kt">string</span> <span class="n">gorunenAd</span> <span class="p">=</span> <span class="n">kullaniciAdi</span> <span class="p">??</span> <span class="s">"Misafir"</span><span class="p">;</span>

<span class="n">Console</span><span class="p">.</span><span class="nf">WriteLine</span><span class="p">(</span><span class="n">gorunenAd</span><span class="p">);</span> <span class="c1">// Misafir</span>
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">is</code> tür denetimi ve örüntü eşleştirme için, <code class="language-plaintext highlighter-rouge">as</code> ise güvenli tür dönüşümü için kullanılır. Ayrıca <code class="language-plaintext highlighter-rouge">nameof(degisken)</code> değişkenin adını metin olarak verir; böylece yeniden adlandırmalara dayanıklı hata mesajları oluşturulur.</p>

<table>
  <thead>
    <tr>
      <th>İşleç</th>
      <th>Amaç</th>
      <th>Başarısızlık davranışı</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">?.</code></td>
      <td>Güvenli üye erişimi</td>
      <td>Null üretir</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">??</code></td>
      <td>Varsayılan değer seçimi</td>
      <td>Sağ tarafı kullanır</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">is</code></td>
      <td>Tür veya örüntü kontrolü</td>
      <td><code class="language-plaintext highlighter-rouge">false</code> üretir</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">as</code></td>
      <td>Referans türü dönüşümü</td>
      <td>Null üretir</td>
    </tr>
  </tbody>
</table>

<h2 id="if-else-ile-karar-vermek">if-else ile karar vermek</h2>

<p><code class="language-plaintext highlighter-rouge">if</code> bloğu koşul doğru olduğunda çalışır. Alternatif yollar <code class="language-plaintext highlighter-rouge">else if</code> ve <code class="language-plaintext highlighter-rouge">else</code> ile tanımlanır.</p>

<div class="language-csharp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">int</span> <span class="n">not</span> <span class="p">=</span> <span class="m">82</span><span class="p">;</span>

<span class="k">if</span> <span class="p">(</span><span class="n">not</span> <span class="p">&gt;=</span> <span class="m">85</span><span class="p">)</span>
<span class="p">{</span>
    <span class="n">Console</span><span class="p">.</span><span class="nf">WriteLine</span><span class="p">(</span><span class="s">"Pek iyi"</span><span class="p">);</span>
<span class="p">}</span>
<span class="k">else</span> <span class="k">if</span> <span class="p">(</span><span class="n">not</span> <span class="p">&gt;=</span> <span class="m">50</span><span class="p">)</span>
<span class="p">{</span>
    <span class="n">Console</span><span class="p">.</span><span class="nf">WriteLine</span><span class="p">(</span><span class="s">"Geçti"</span><span class="p">);</span>
<span class="p">}</span>
<span class="k">else</span>
<span class="p">{</span>
    <span class="n">Console</span><span class="p">.</span><span class="nf">WriteLine</span><span class="p">(</span><span class="s">"Tekrar dene"</span><span class="p">);</span>
<span class="p">}</span>
</code></pre></div></div>

<p>Basit seçimlerde üçlü koşul operatörü kullanılabilir: <code class="language-plaintext highlighter-rouge">sonuc = kosul ? dogruDeger : yanlisDeger;</code>. Ancak iç içe üçlü ifadeler kodu bulmacaya çevirebilir; okunabilirlik her zaman kısalıktan değerlidir.</p>

<h2 id="döngüsel-iterasyon-mekanizmaları">Döngüsel iterasyon mekanizmaları</h2>

<p>Döngüler tekrar eden işleri otomatikleştirir. Hangi döngünün seçileceği, tekrar sayısının bilinip bilinmemesine bağlıdır.</p>

<table>
  <thead>
    <tr>
      <th>Döngü</th>
      <th>Ne zaman tercih edilir?</th>
      <th>Özellik</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">for</code></td>
      <td>Tekrar sayısı biliniyorsa</td>
      <td>Sayaç kontrolü sunar</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">while</code></td>
      <td>Devam koşulu önemliyse</td>
      <td>Koşulu başta sınar</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">do-while</code></td>
      <td>İşlem en az bir kez yapılacaksa</td>
      <td>Koşulu sonda sınar</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">foreach</code></td>
      <td>Koleksiyon gezilecekse</td>
      <td>İndeks yönetimi gerektirmez</td>
    </tr>
  </tbody>
</table>

<div class="language-csharp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">string</span><span class="p">[]</span> <span class="n">diller</span> <span class="p">=</span> <span class="p">{</span> <span class="s">"C#"</span><span class="p">,</span> <span class="s">"Java"</span><span class="p">,</span> <span class="s">"Python"</span> <span class="p">};</span>

<span class="k">foreach</span> <span class="p">(</span><span class="kt">string</span> <span class="n">dil</span> <span class="k">in</span> <span class="n">diller</span><span class="p">)</span>
<span class="p">{</span>
    <span class="k">if</span> <span class="p">(</span><span class="n">dil</span> <span class="p">==</span> <span class="s">"Java"</span><span class="p">)</span>
        <span class="k">continue</span><span class="p">;</span> <span class="c1">// Bu turu atlar</span>

    <span class="n">Console</span><span class="p">.</span><span class="nf">WriteLine</span><span class="p">(</span><span class="n">dil</span><span class="p">);</span>
<span class="p">}</span>
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">continue</code> mevcut turu atlatırken <code class="language-plaintext highlighter-rouge">break</code> döngüyü tamamen bitirir. Sonsuz döngülerden kaçınmak için <code class="language-plaintext highlighter-rouge">while</code> koşulunu etkileyen değerin gerçekten değiştiğinden emin olun. Özetle operatörler veriyi işler, koşullar yolu seçer, döngüler ise işi tekrarlar; bu üçlü, neredeyse bütün C# uygulamalarının kontrol merkezidir.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="c#" /><category term="operatörler" /><category term="if-else" /><category term="döngüler" /><category term="programlama" /><category term="kontrol-akışı" /><summary type="html"><![CDATA[Bir C# programı yalnızca yukarıdan aşağıya çalışan komutlardan oluşmaz. Değerleri karşılaştırır, koşullara göre karar verir ve gerektiğinde aynı işlemi tekrarlar. Operatörler bu kararların kelimeleri, kontrol blokları ise programın trafik ışıklarıdır. Gelin C# kodunun nasıl düşündüğünü adım adım inceleyelim.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/c-operatorler-ve-81.png" /><media:content medium="image" url="https://program.sonsuz.us/img/c-operatorler-ve-81.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">C++ Şablonlarında Specialization ve Overloading: Derleyicinin İnce Seçim Oyunu</title><link href="https://program.sonsuz.us/posts/c-sablonlarinda-specialization-ve-overloading-derleyicinin-ince-secim-oyunu/" rel="alternate" type="text/html" title="C++ Şablonlarında Specialization ve Overloading: Derleyicinin İnce Seçim Oyunu" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/c-sablonlarinda-specialization-ve-overloading-derleyicinin-ince-secim-oyunu</id><content type="html" xml:base="https://program.sonsuz.us/posts/c-sablonlarinda-specialization-ve-overloading-derleyicinin-ince-secim-oyunu/"><![CDATA[<p><img src="/img/c-sablonlarinda-specialization-82.svg" alt="c-sablonlarinda-specialization-82" /></p>

<p>C++ şablonlarında özelleştirme ve aşırı yükleme aynı hedefe gidiyormuş gibi görünür: belirli türlerde farklı davranmak. Fakat derleyicinin gözünde bunlar iki ayrı mekanizmadır. Overloading adaylar arasındaki yarışı belirlerken specialization, yarışı kazanan şablonun özel bir sürümünün bulunup bulunmadığına bakar. Küçük görünen bu sıra farkı, şaşırtıcı sonuçların kaynağıdır.</p>

<p>``</p>

<h2 id="i̇ki-mekanizmanın-temel-anlamı">İki mekanizmanın temel anlamı</h2>

<p>Bir fonksiyon şablonunu aşırı yüklediğimizde derleyicinin aday listesine yeni bir fonksiyon şablonu ekleriz. Açık özelleştirme ise yeni ve bağımsız bir aday oluşturmaz; mevcut birincil şablonun belirli argümanlar için alternatif uygulamasını tanımlar.</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="cp">#include</span> <span class="cpf">&lt;iostream&gt;</span><span class="cp">
</span>
<span class="k">template</span><span class="o">&lt;</span><span class="k">typename</span> <span class="nc">T</span><span class="p">&gt;</span>
<span class="kt">void</span> <span class="nf">goster</span><span class="p">(</span><span class="n">T</span><span class="p">)</span> <span class="p">{</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">"Genel sürüm</span><span class="se">\n</span><span class="s">"</span><span class="p">;</span>
<span class="p">}</span>

<span class="k">template</span><span class="o">&lt;</span><span class="p">&gt;</span>
<span class="kt">void</span> <span class="n">goster</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span><span class="p">(</span><span class="kt">int</span><span class="p">)</span> <span class="p">{</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">"int özelleştirmesi</span><span class="se">\n</span><span class="s">"</span><span class="p">;</span>
<span class="p">}</span>

<span class="k">template</span><span class="o">&lt;</span><span class="k">typename</span> <span class="nc">T</span><span class="p">&gt;</span>
<span class="kt">void</span> <span class="nf">goster</span><span class="p">(</span><span class="n">T</span><span class="o">*</span><span class="p">)</span> <span class="p">{</span>
    <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">"İşaretçi overload'u</span><span class="se">\n</span><span class="s">"</span><span class="p">;</span>
<span class="p">}</span>
</code></pre></div></div>

<p>Burada üç bildirim varmış gibi görünse de overload çözümlemesinde yalnızca <code class="language-plaintext highlighter-rouge">goster(T)</code> ve <code class="language-plaintext highlighter-rouge">goster(T*)</code> yarışır. <code class="language-plaintext highlighter-rouge">goster&lt;int&gt;</code> ise ilk şablona bağlı bir açık özelleştirmedir.</p>

<table>
  <thead>
    <tr>
      <th>Özellik</th>
      <th>Overloading</th>
      <th>Specialization</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Yeni aday oluşturur mu?</td>
      <td>Evet</td>
      <td>Hayır</td>
    </tr>
    <tr>
      <td>Fonksiyonlarda kısmi biçimi var mı?</td>
      <td>Overload ile benzetilebilir</td>
      <td>Hayır</td>
    </tr>
    <tr>
      <td>Seçim zamanı</td>
      <td>Overload çözümlemesi sırasında</td>
      <td>Birincil şablon seçildikten sonra</td>
    </tr>
    <tr>
      <td>Kapsam</td>
      <td>Fonksiyon ve normal fonksiyonlar</td>
      <td>Birincil şablona bağlı</td>
    </tr>
    <tr>
      <td>Temel amaç</td>
      <td>Farklı parametre biçimleri</td>
      <td>Belirli argüman için özel uygulama</td>
    </tr>
  </tbody>
</table>

<h2 id="derleyicinin-seçim-sırası">Derleyicinin seçim sırası</h2>

<p>Basitleştirilmiş süreç şöyledir:</p>

<ol>
  <li>Görünür fonksiyonlar ve fonksiyon şablonları aday kümeye alınır.</li>
  <li>Şablon argüman çıkarımı yapılır.</li>
  <li>Dönüşüm kalitesi ve şablonların kısmi sıralaması değerlendirilir.</li>
  <li>En iyi overload seçilir.</li>
  <li>Kazanan bir fonksiyon şablonuysa ona ait açık özelleştirme aranır.</li>
</ol>

<p>Bunu kabaca</p>

\[\text{çağrılacak fonksiyon} = \operatorname{specialization}(\operatorname{bestOverload}(C))\]

<p>şeklinde düşünebiliriz. Buradaki $C$, uygun adaylar kümesidir. İşlemlerin sırası ters değildir; specialization önce yarışıp overload’u yenemez.</p>

<h2 id="klasik-işaretçi-sürprizi">Klasik işaretçi sürprizi</h2>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">int</span><span class="o">*</span> <span class="n">p</span> <span class="o">=</span> <span class="nb">nullptr</span><span class="p">;</span>
<span class="n">goster</span><span class="p">(</span><span class="n">p</span><span class="p">);</span>
</code></pre></div></div>

<p>İlk bakışta <code class="language-plaintext highlighter-rouge">T = int*</code> olduğundan genel şablonun <code class="language-plaintext highlighter-rouge">int*</code> özelleştirmesinin aranacağı düşünülebilir. Ancak <code class="language-plaintext highlighter-rouge">goster(T*)</code>, <code class="language-plaintext highlighter-rouge">int*</code> argümanı için <code class="language-plaintext highlighter-rouge">goster(T)</code> şablonundan daha özeldir. Dolayısıyla pointer overload’u yarışı kazanır. Derleyici artık yalnızca bu kazanan şablona bağlı bir explicit specialization olup olmadığına bakar; diğer birincil şablonun özelleştirmesine geri dönmez.</p>

<p>Bu nedenle bir specialization’ın hangi birincil şablona bağlı olduğu kritik önemdedir. Bildirim sırası ve specialization bildiriminin çağrıdan önce görünür olması da ayrı derleme birimlerinde ciddi farklar yaratabilir. Açık özelleştirme, örtük örneklemeye yol açan ilk kullanımdan önce bildirilmelidir.</p>

<h2 id="neden-fonksiyon-şablonları-kısmen-özelleştirilemez">Neden fonksiyon şablonları kısmen özelleştirilemez?</h2>

<p>Sınıf şablonlarında kısmi özelleştirme geçerlidir:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">template</span><span class="o">&lt;</span><span class="k">typename</span> <span class="nc">T</span><span class="p">&gt;</span>
<span class="k">struct</span> <span class="nc">Bilgi</span><span class="p">;</span>

<span class="k">template</span><span class="o">&lt;</span><span class="k">typename</span> <span class="nc">T</span><span class="p">&gt;</span>
<span class="k">struct</span> <span class="nc">Bilgi</span><span class="o">&lt;</span><span class="n">T</span><span class="o">*&gt;</span> <span class="p">{</span>
    <span class="k">static</span> <span class="k">constexpr</span> <span class="kt">bool</span> <span class="n">pointer</span> <span class="o">=</span> <span class="nb">true</span><span class="p">;</span>
<span class="p">};</span>
</code></pre></div></div>

<p>Fakat aşağıdaki fonksiyon biçimi geçersizdir:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">template</span><span class="o">&lt;</span><span class="k">typename</span> <span class="nc">T</span><span class="p">&gt;</span>
<span class="kt">void</span> <span class="n">isle</span><span class="o">&lt;</span><span class="n">T</span><span class="o">*&gt;</span><span class="p">(</span><span class="n">T</span><span class="o">*</span><span class="p">);</span> <span class="c1">// Geçersiz kısmi specialization</span>
</code></pre></div></div>

<p>Fonksiyonlarda aynı niyet overload ile ifade edilir:</p>

<div class="language-cpp highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">template</span><span class="o">&lt;</span><span class="k">typename</span> <span class="nc">T</span><span class="p">&gt;</span>
<span class="kt">void</span> <span class="nf">isle</span><span class="p">(</span><span class="n">T</span><span class="o">*</span><span class="p">)</span> <span class="p">{</span>
    <span class="c1">// Türetilen her işaretçi türü için ortak davranış</span>
<span class="p">}</span>
</code></pre></div></div>

<p>Bunun önemli nedeni, fonksiyonlarda zaten overload çözümlemesi bulunmasıdır. Kısmi specialization da eklenseydi iki ayrı sıralama sistemi birbiriyle çakışabilirdi.</p>

<h2 id="pratik-tercih-rehberi">Pratik tercih rehberi</h2>

<p>Bir tür ailesini yakalamak istiyorsanız overload kullanın. Yalnızca tek ve kesin bir şablon argümanı kombinasyonunda davranışı değiştirecekseniz explicit specialization düşünülebilir. Bununla birlikte fonksiyonlarda overload çoğu zaman daha okunabilir ve öngörülebilirdir.</p>

<p>Modern C++ kodunda <code class="language-plaintext highlighter-rouge">if constexpr</code>, kavramlar ve <code class="language-plaintext highlighter-rouge">requires</code> ifadeleri de güçlü alternatiflerdir. Özellikle kısıtlı overload’lar, niyeti doğrudan tür sistemi üzerinden anlatır. Altın kural şudur: specialization’ı bağımsız yarışmacı sanmayın; o, ancak bağlı olduğu şablon yarışı kazandığında sahneye çıkan yedek oyuncudur.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="c++" /><category term="templates" /><category term="specialization" /><category term="overloading" /><category term="derleyici" /><category term="generic-programming" /><summary type="html"><![CDATA[C++ şablonlarında özelleştirme ve aşırı yükleme aynı hedefe gidiyormuş gibi görünür: belirli türlerde farklı davranmak. Fakat derleyicinin gözünde bunlar iki ayrı mekanizmadır. Overloading adaylar arasındaki yarışı belirlerken specialization, yarışı kazanan şablonun özel bir sürümünün bulunup bulunmadığına bakar. Küçük görünen bu sıra farkı, şaşırtıcı sonuçların kaynağıdır.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/c-sablonlarinda-specialization-82.png" /><media:content medium="image" url="https://program.sonsuz.us/img/c-sablonlarinda-specialization-82.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">Fazladan Eklem, Fazladan Kaçış: Redundant Robot Kollarda Engel Atlama</title><link href="https://program.sonsuz.us/posts/fazladan-eklem-fazladan-kacis-redundant-robot-kollarda-engel-atlama/" rel="alternate" type="text/html" title="Fazladan Eklem, Fazladan Kaçış: Redundant Robot Kollarda Engel Atlama" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/fazladan-eklem-fazladan-kacis-redundant-robot-kollarda-engel-atlama</id><content type="html" xml:base="https://program.sonsuz.us/posts/fazladan-eklem-fazladan-kacis-redundant-robot-kollarda-engel-atlama/"><![CDATA[<p>Bir robot kolunun görevi yalnızca hedefe ulaşmak değildir; bunu masaya, duvara veya merakla yaklaşan başka bir robota çarpmadan yapması gerekir. Redundant, yani artıklıklı çok eklemli kollar tam bu noktada avantaj sağlar. Uç efektörün konumu değişmeden dirseklerini ve diğer eklemlerini hareket ettirebilen bu robotlar, engeller karşısında adeta “hedefe bakarken belini büken” mekanik akrobatlara dönüşür.
``</p>
<h2 id="artıklılık-ne-anlama-gelir">Artıklılık ne anlama gelir?</h2>

<p>Bir manipülatörün eklem değişkenlerini $q \in R^n$, uç efektör görevini ise $x \in R^m$ ile gösterelim. İleri kinematik ilişki</p>

\[x = f(q)\]

<p>şeklindedir. Eğer eklem sayısı görev uzayının boyutundan büyükse, yani $n &gt; m$ ise sistem redundant kabul edilir. Örneğin üç boyutlu uzayda yalnızca uç noktanın konumunu kontrol etmek için üç bağımsız değişken yeterliyken yedi eklemli bir kol dört adet fazladan serbestlik derecesine sahiptir.</p>

<p>Bu fazlalık gereksiz değildir. Aynı uç efektör konumunu üreten birden fazla eklem yapılandırması bulunabilir. Robot böylece ana görevi bozmadan dirseğini bir engelden uzaklaştırabilir, eklem sınırlarından kaçabilir veya daha rahat bir duruş seçebilir.</p>

<table>
  <thead>
    <tr>
      <th>Özellik</th>
      <th>Minimum serbestlikli kol</th>
      <th>Redundant kol</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Aynı hedef için çözüm</td>
      <td>Genellikle sınırlı</td>
      <td>Çok sayıda</td>
    </tr>
    <tr>
      <td>Engel çevresinde hareket</td>
      <td>Kısıtlı</td>
      <td>Esnek</td>
    </tr>
    <tr>
      <td>Eklem sınırlarından kaçış</td>
      <td>Zor</td>
      <td>İkincil görevle mümkün</td>
    </tr>
    <tr>
      <td>Hesaplama maliyeti</td>
      <td>Daha düşük</td>
      <td>Daha yüksek</td>
    </tr>
    <tr>
      <td>Arıza toleransı</td>
      <td>Düşük</td>
      <td>Görece yüksek</td>
    </tr>
  </tbody>
</table>

<p><img src="/img/fazladan-eklem-fazladan-66.svg" alt="fazladan-eklem-fazladan-66" /></p>

<h2 id="jacobian-ve-sıfır-uzayı">Jacobian ve sıfır uzayı</h2>

<p>Eklem hızları ile uç efektör hızı arasındaki ilişki Jacobian matrisiyle kurulur:</p>

\[\dot{x} = J(q)\dot{q}\]

<p>Redundant bir sistemde ters çözüm tek değildir. Yaygın hız çözümü şöyledir:</p>

\[\dot{q} = J^+\dot{x} + (I-J^+J)z\]

<p>Burada $J^+$ Jacobian’ın sözde tersidir. İlk terim uç efektörü hedeflenen yönde hareket ettirir. İkinci terim ise Jacobian’ın sıfır uzayında kalır; başka bir deyişle uç efektör hareketini değiştirmeden eklemleri oynatır. Engel kaçınma sihrinin büyük bölümü bu ikinci terimdedir.</p>

<p>$z$ vektörü, robotu engelden uzaklaştıran bir maliyet fonksiyonunun negatif gradyanı olarak seçilebilir:</p>

\[z = -k \nabla H(q)\]

<p>$H(q)$ robot ile engel arasındaki mesafe azaldıkça büyüyen bir ceza fonksiyonu olabilir. Böylece robot bir eliyle hedefe ilerlerken “dirseğini içeri çekebilir.”</p>

<h2 id="basit-bir-hesaplama-örneği">Basit bir hesaplama örneği</h2>

<p>Aşağıdaki Python kodu, ana uç efektör hızına sıfır uzayı üzerinden ikincil bir kaçınma hareketi ekler:</p>

<div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kn">import</span> <span class="n">numpy</span> <span class="k">as</span> <span class="n">np</span>

<span class="k">def</span> <span class="nf">redundant_velocity</span><span class="p">(</span><span class="n">J</span><span class="p">,</span> <span class="n">target_velocity</span><span class="p">,</span> <span class="n">avoidance_gradient</span><span class="p">,</span> <span class="n">gain</span><span class="o">=</span><span class="mf">0.4</span><span class="p">):</span>
    <span class="n">J_pinv</span> <span class="o">=</span> <span class="n">np</span><span class="p">.</span><span class="n">linalg</span><span class="p">.</span><span class="nf">pinv</span><span class="p">(</span><span class="n">J</span><span class="p">)</span>
    <span class="n">identity</span> <span class="o">=</span> <span class="n">np</span><span class="p">.</span><span class="nf">eye</span><span class="p">(</span><span class="n">J</span><span class="p">.</span><span class="n">shape</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>

    <span class="n">primary</span> <span class="o">=</span> <span class="n">J_pinv</span> <span class="o">@</span> <span class="n">target_velocity</span>
    <span class="n">null_space</span> <span class="o">=</span> <span class="n">identity</span> <span class="o">-</span> <span class="n">J_pinv</span> <span class="o">@</span> <span class="n">J</span>
    <span class="n">secondary</span> <span class="o">=</span> <span class="n">null_space</span> <span class="o">@</span> <span class="p">(</span><span class="o">-</span><span class="n">gain</span> <span class="o">*</span> <span class="n">avoidance_gradient</span><span class="p">)</span>

    <span class="k">return</span> <span class="n">primary</span> <span class="o">+</span> <span class="n">secondary</span>
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">primary</code> hedefe ulaşma görevini gerçekleştirir. <code class="language-plaintext highlighter-rouge">secondary</code> ise engel maliyetini azaltmaya çalışır. <code class="language-plaintext highlighter-rouge">null_space</code> izdüşümü sayesinde ikincil hareket, ideal matematiksel koşullarda uç efektörün istenen hızını bozmaz.</p>

<h2 id="potansiyel-alan-yaklaşımı">Potansiyel alan yaklaşımı</h2>

<p>Engeller çoğu zaman itici potansiyel alanlarla modellenir. Engel ile robot noktası arasındaki mesafe $d$, etkinin başladığı güvenli mesafe $d_0$ olsun:</p>

\[U(d) = \frac{1}{2}\eta\left(\frac{1}{d}-\frac{1}{d_0}\right)^2, \quad d &lt; d_0\]

<p>Robot engelden uzaktaysa ceza sıfırdır; yaklaştıkça hızla büyür. Bu yöntem sezgiseldir fakat yerel minimumlara takılabilir. Ayrıca yalnızca uç efektörü değil, dirsek ve bağlantılar üzerindeki örnek noktaları da kontrol etmek gerekir.</p>

<table>
  <thead>
    <tr>
      <th>Yaklaşım</th>
      <th>Avantaj</th>
      <th>Dezavantaj</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Potansiyel alan</td>
      <td>Hızlı ve sezgisel</td>
      <td>Yerel minimum oluşturabilir</td>
    </tr>
    <tr>
      <td>Sıfır uzayı kontrolü</td>
      <td>Ana görevi korur</td>
      <td>Tekilliklere duyarlıdır</td>
    </tr>
    <tr>
      <td>Optimizasyon tabanlı kontrol</td>
      <td>Kısıtları birlikte işler</td>
      <td>Daha fazla hesaplama ister</td>
    </tr>
  </tbody>
</table>

<p>Sonuç olarak fazladan serbestlik derecesi, robota yalnızca daha fazla hareket değil, aynı hedefe giderken daha iyi hareket seçme özgürlüğü verir. Doğru kontrol algoritmasıyla redundant kol; engellerden kaçınabilir, eklem sınırlarını koruyabilir ve çalışma alanında çok daha güvenli davranabilir.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="robotik" /><category term="redundant manipülatör" /><category term="engel kaçınma" /><category term="ters kinematik" /><category term="jacobian" /><category term="optimizasyon" /><summary type="html"><![CDATA[Bir robot kolunun görevi yalnızca hedefe ulaşmak değildir; bunu masaya, duvara veya merakla yaklaşan başka bir robota çarpmadan yapması gerekir. Redundant, yani artıklıklı çok eklemli kollar tam bu noktada avantaj sağlar. Uç efektörün konumu değişmeden dirseklerini ve diğer eklemlerini hareket ettirebilen bu robotlar, engeller karşısında adeta “hedefe bakarken belini büken” mekanik akrobatlara dönüşür.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/fazladan-eklem-fazladan-66.png" /><media:content medium="image" url="https://program.sonsuz.us/img/fazladan-eklem-fazladan-66.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">Java Operatörleri ve Kontrol İfadeleriyle Program Akışını Yönetmek</title><link href="https://program.sonsuz.us/posts/java-operatorleri-ve-kontrol-ifadeleriyle-program-akisini-yonetmek/" rel="alternate" type="text/html" title="Java Operatörleri ve Kontrol İfadeleriyle Program Akışını Yönetmek" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/java-operatorleri-ve-kontrol-ifadeleriyle-program-akisini-yonetmek</id><content type="html" xml:base="https://program.sonsuz.us/posts/java-operatorleri-ve-kontrol-ifadeleriyle-program-akisini-yonetmek/"><![CDATA[<p>Bir Java programı yalnızca yukarıdan aşağıya çalışan komutlardan oluşsaydı, hesap makinesinden biraz daha heyecanlı uygulamalar geliştirmek zor olurdu. Operatörler verileri işlerken kontrol ifadeleri programın hangi yolu izleyeceğine karar verir. Başka bir deyişle operatörler soruları hazırlar, karar yapıları cevapları değerlendirir, döngüler ise gerekli işleri sabırla tekrarlar.
``</p>
<h2 id="operatörler-programın-hesaplama-araçları">Operatörler: Programın hesaplama araçları</h2>

<p>Operatörler, bir veya daha fazla değer üzerinde işlem yapan sembollerdir. Örneğin <code class="language-plaintext highlighter-rouge">+</code> toplama yaparken <code class="language-plaintext highlighter-rouge">&gt;</code> iki değeri karşılaştırır. Bir ifadenin sonucu başka bir operatörün girdisi olabilir. Bu nedenle işlem önceliğini anlamak önemlidir.</p>

<p>Örneğin aşağıdaki matematiksel ifade Java’da da aynı öncelik mantığıyla değerlendirilir:</p>

\[sonuc = 10 + 4 \times 2 = 18\]

<p>Çarpma önce çalışır. Sonucun <code class="language-plaintext highlighter-rouge">28</code> olması isteniyorsa parantez kullanılmalıdır: <code class="language-plaintext highlighter-rouge">(10 + 4) * 2</code>.</p>

<table>
  <thead>
    <tr>
      <th>Operatör grubu</th>
      <th>Örnekler</th>
      <th>Görevi</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Aritmetik</td>
      <td><code class="language-plaintext highlighter-rouge">+</code>, <code class="language-plaintext highlighter-rouge">-</code>, <code class="language-plaintext highlighter-rouge">*</code>, <code class="language-plaintext highlighter-rouge">/</code>, <code class="language-plaintext highlighter-rouge">%</code></td>
      <td>Matematiksel işlem yapar</td>
    </tr>
    <tr>
      <td>Karşılaştırma</td>
      <td><code class="language-plaintext highlighter-rouge">==</code>, <code class="language-plaintext highlighter-rouge">!=</code>, <code class="language-plaintext highlighter-rouge">&lt;</code>, <code class="language-plaintext highlighter-rouge">&gt;=</code></td>
      <td><code class="language-plaintext highlighter-rouge">boolean</code> sonuç üretir</td>
    </tr>
    <tr>
      <td>Mantıksal</td>
      <td><code class="language-plaintext highlighter-rouge">&amp;&amp;</code>, <code class="language-plaintext highlighter-rouge">||</code>, <code class="language-plaintext highlighter-rouge">!</code></td>
      <td>Koşulları birleştirir veya tersine çevirir</td>
    </tr>
    <tr>
      <td>Atama</td>
      <td><code class="language-plaintext highlighter-rouge">=</code>, <code class="language-plaintext highlighter-rouge">+=</code>, <code class="language-plaintext highlighter-rouge">-=</code></td>
      <td>Değişkene değer atar veya günceller</td>
    </tr>
    <tr>
      <td>Artırma-azaltma</td>
      <td><code class="language-plaintext highlighter-rouge">++</code>, <code class="language-plaintext highlighter-rouge">--</code></td>
      <td>Sayıyı bir artırır veya azaltır</td>
    </tr>
  </tbody>
</table>

<p><img src="/img/java-operatorleri-ve-60.svg" alt="java-operatorleri-ve-60" /></p>

<p>Mod alma operatörü <code class="language-plaintext highlighter-rouge">%</code>, özellikle çift-tek kontrolünde kullanışlıdır. Bir $n$ sayısı için $n \bmod 2 = 0$ ise sayı çifttir.</p>

<h2 id="karar-yapıları-yol-ayrımındaki-java">Karar yapıları: Yol ayrımındaki Java</h2>

<p><code class="language-plaintext highlighter-rouge">if</code>, <code class="language-plaintext highlighter-rouge">else if</code> ve <code class="language-plaintext highlighter-rouge">else</code>, koşullara göre farklı kod blokları çalıştırır. Koşulun sonucu mutlaka <code class="language-plaintext highlighter-rouge">true</code> veya <code class="language-plaintext highlighter-rouge">false</code> olmalıdır.</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">int</span> <span class="n">puan</span> <span class="o">=</span> <span class="mi">78</span><span class="o">;</span>

<span class="k">if</span> <span class="o">(</span><span class="n">puan</span> <span class="o">&gt;=</span> <span class="mi">85</span><span class="o">)</span> <span class="o">{</span>
    <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Pekiyi"</span><span class="o">);</span>
<span class="o">}</span> <span class="k">else</span> <span class="k">if</span> <span class="o">(</span><span class="n">puan</span> <span class="o">&gt;=</span> <span class="mi">50</span><span class="o">)</span> <span class="o">{</span>
    <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Geçti"</span><span class="o">);</span>
<span class="o">}</span> <span class="k">else</span> <span class="o">{</span>
    <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Kaldı"</span><span class="o">);</span>
<span class="o">}</span>
</code></pre></div></div>

<p>Bu kod, karşılaştırma operatörleriyle puanı sınıflandırır. Koşullar yukarıdan aşağıya sınanır ve ilk doğru bloğun ardından yapı sona erer. Dolayısıyla daha özel veya yüksek eşikli koşulların önce yazılması önemlidir.</p>

<p>Sabit seçeneklerin bulunduğu durumlarda <code class="language-plaintext highlighter-rouge">switch</code> daha okunaklı olabilir:</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nc">String</span> <span class="n">rol</span> <span class="o">=</span> <span class="s">"editor"</span><span class="o">;</span>

<span class="k">switch</span> <span class="o">(</span><span class="n">rol</span><span class="o">)</span> <span class="o">{</span>
    <span class="k">case</span> <span class="s">"admin"</span> <span class="o">-&gt;</span> <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Tam yetki"</span><span class="o">);</span>
    <span class="k">case</span> <span class="s">"editor"</span> <span class="o">-&gt;</span> <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"İçerik düzenleme yetkisi"</span><span class="o">);</span>
    <span class="k">default</span> <span class="o">-&gt;</span> <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Sınırlı yetki"</span><span class="o">);</span>
<span class="o">}</span>
</code></pre></div></div>

<table>
  <thead>
    <tr>
      <th>Yapı</th>
      <th>En uygun kullanım</th>
      <th>Güçlü yönü</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">if-else</code></td>
      <td>Aralıklar ve karmaşık koşullar</td>
      <td>Esneklik</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">switch</code></td>
      <td>Belirli, ayrık seçenekler</td>
      <td>Okunabilirlik</td>
    </tr>
    <tr>
      <td>Üçlü operatör</td>
      <td>Kısa değer seçimi</td>
      <td>Az kod</td>
    </tr>
  </tbody>
</table>

<p>Üçlü operatörün biçimi <code class="language-plaintext highlighter-rouge">koşul ? doğruDeğer : yanlışDeğer</code> şeklindedir. Örneğin <code class="language-plaintext highlighter-rouge">yas &gt;= 18 ? "Yetişkin" : "Çocuk"</code> ifadesi kısa bir karar üretir; ancak iç içe kullanılırsa okunabilirliği hızla düşürür.</p>

<h2 id="döngüler-tekrarın-kontrollü-hâli">Döngüler: Tekrarın kontrollü hâli</h2>

<p>Döngüler, aynı işlemi belirli bir koşul sağlandığı sürece tekrarlar. <code class="language-plaintext highlighter-rouge">for</code> tekrar sayısı bilindiğinde, <code class="language-plaintext highlighter-rouge">while</code> koşul ön planda olduğunda, <code class="language-plaintext highlighter-rouge">do-while</code> ise bloğun en az bir kez çalışması gerektiğinde tercih edilir.</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">int</span> <span class="n">toplam</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span>

<span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="mi">5</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span>
    <span class="n">toplam</span> <span class="o">+=</span> <span class="n">i</span><span class="o">;</span>
<span class="o">}</span>

<span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">toplam</span><span class="o">);</span> <span class="c1">// 15</span>
</code></pre></div></div>

<p>Bu döngü $1+2+3+4+5=15$ toplamını hesaplar. Başlangıç değeri, devam koşulu ve artış işlemi aynı satırda görüldüğü için akış kolayca izlenebilir.</p>

<p><code class="language-plaintext highlighter-rouge">break</code> döngüyü tamamen sonlandırırken <code class="language-plaintext highlighter-rouge">continue</code> yalnızca mevcut turu atlar. Bunlar güçlü araçlardır; gereğinden fazla kullanılmaları akışı takip etmeyi zorlaştırabilir.</p>

<h2 id="kısa-devre-değerlendirmesi">Kısa devre değerlendirmesi</h2>

<p>Mantıksal <code class="language-plaintext highlighter-rouge">&amp;&amp;</code> operatörü ilk koşul yanlışsa ikinci koşulu çalıştırmaz. <code class="language-plaintext highlighter-rouge">||</code> ise ilk koşul doğruysa devamını değerlendirmez:</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">if</span> <span class="o">(</span><span class="n">kullanici</span> <span class="o">!=</span> <span class="kc">null</span> <span class="o">&amp;&amp;</span> <span class="n">kullanici</span><span class="o">.</span><span class="na">isActive</span><span class="o">())</span> <span class="o">{</span>
    <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Giriş başarılı"</span><span class="o">);</span>
<span class="o">}</span>
</code></pre></div></div>

<p>Burada önce <code class="language-plaintext highlighter-rouge">null</code> kontrolü yapılır. Böylece var olmayan bir nesne üzerinde metot çağrılması ve <code class="language-plaintext highlighter-rouge">NullPointerException</code> oluşması engellenir.</p>

<p>Sonuç olarak operatörler veriyi dönüştürür, karar ifadeleri uygun yolu seçer ve döngüler tekrarları yönetir. Sağlam bir Java programında bu üçlü birlikte çalışır: doğru koşul kurulur, akış bilinçli biçimde yönlendirilir ve her tekrarın ne zaman biteceği açıkça tanımlanır.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="java" /><category term="operatörler" /><category term="kontrol-akışı" /><category term="döngüler" /><category term="karar-yapıları" /><category term="programlama" /><summary type="html"><![CDATA[Bir Java programı yalnızca yukarıdan aşağıya çalışan komutlardan oluşsaydı, hesap makinesinden biraz daha heyecanlı uygulamalar geliştirmek zor olurdu. Operatörler verileri işlerken kontrol ifadeleri programın hangi yolu izleyeceğine karar verir. Başka bir deyişle operatörler soruları hazırlar, karar yapıları cevapları değerlendirir, döngüler ise gerekli işleri sabırla tekrarlar.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/java-operatorleri-ve-60.png" /><media:content medium="image" url="https://program.sonsuz.us/img/java-operatorleri-ve-60.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">Java Tarihçesi ve Evrimi: Oak Ağacından JVM Dünyasına</title><link href="https://program.sonsuz.us/posts/java-tarihcesi-ve-evrimi-oak-agacindan-jvm-dunyasina/" rel="alternate" type="text/html" title="Java Tarihçesi ve Evrimi: Oak Ağacından JVM Dünyasına" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/java-tarihcesi-ve-evrimi-oak-agacindan-jvm-dunyasina</id><content type="html" xml:base="https://program.sonsuz.us/posts/java-tarihcesi-ve-evrimi-oak-agacindan-jvm-dunyasina/"><![CDATA[<p>Java, bugün kurumsal uygulamalardan Android ekosistemine kadar pek çok alanda karşımıza çıksa da yolculuğuna web için değil, etkileşimli elektronik cihazlar için başladı. Dilin asıl başarısı yalnızca sözdiziminden kaynaklanmadı; farklı donanımlarda aynı programı çalıştırmayı hedefleyen taşınabilir mimarisi, yazılım dünyasının önemli problemlerinden birine güçlü bir cevap verdi.</p>

<p>``</p>

<h2 id="green-project-ve-oakın-doğuşu">Green Project ve Oak’ın Doğuşu</h2>

<p>Java’nın hikâyesi 1991 yılında Sun Microsystems bünyesindeki <strong>Green Project</strong> ile başladı. James Gosling, Mike Sheridan ve Patrick Naughton gibi mühendisler, televizyon kutuları ve ev cihazları için güvenilir bir yazılım platformu geliştirmeye çalışıyordu. C ve C++ güçlüydü; ancak donanıma bağımlılık, elle bellek yönetimi ve işaretçi hataları bu cihazlar için ciddi risk oluşturuyordu.</p>

<p>Gosling tarafından geliştirilen dil önce, ofisinin önündeki ağaçtan esinlenilerek <strong>Oak</strong> adını aldı. Oak isminin başka bir şirket tarafından tescillenmiş olması nedeniyle dilin adı daha sonra Java olarak değiştirildi. Projenin cihaz pazarı beklenen hızda büyümese de internetin yükselişi, taşınabilir kod fikrine yeni bir sahne hazırladı. Java, 1995 yılında resmen tanıtıldı.</p>

<p>Java’nın temel felsefesi şu sloganla özetlendi: <strong>Write Once, Run Anywhere</strong> — bir kez yaz, her yerde çalıştır.</p>

<table>
  <thead>
    <tr>
      <th>Özellik</th>
      <th>C/C++ yaklaşımı</th>
      <th>Java yaklaşımı</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Derleme hedefi</td>
      <td>Belirli işlemci ve işletim sistemi</td>
      <td>JVM üzerinde çalışan bayt kod</td>
    </tr>
    <tr>
      <td>Bellek yönetimi</td>
      <td>Çoğunlukla geliştiriciye ait</td>
      <td>Garbage Collector tarafından yönetilir</td>
    </tr>
    <tr>
      <td>İşaretçiler</td>
      <td>Doğrudan kullanılabilir</td>
      <td>Güvenli referans modeli kullanılır</td>
    </tr>
    <tr>
      <td>Taşınabilirlik</td>
      <td>Yeniden derleme gerekebilir</td>
      <td>Uygun JVM yeterlidir</td>
    </tr>
    <tr>
      <td>Güvenlik</td>
      <td>Ortama ve koda bağlıdır</td>
      <td>Doğrulama ve çalışma zamanı kontrolleri vardır</td>
    </tr>
  </tbody>
</table>

<p><img src="/img/java-tarihcesi-ve-53.svg" alt="java-tarihcesi-ve-53" /></p>

<h2 id="kaynak-koddan-bayt-koda">Kaynak Koddan Bayt Koda</h2>

<p>Java derleyicisi, kaynak kodunu doğrudan belirli bir işlemcinin makine diline dönüştürmez. Bunun yerine JVM’nin anlayabileceği ara temsil olan <strong>bayt kodu</strong> üretir.</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kd">public</span> <span class="kd">class</span> <span class="nc">MerhabaJVM</span> <span class="o">{</span>
    <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="nc">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span>
        <span class="kt">int</span> <span class="n">javaYasi</span> <span class="o">=</span> <span class="mi">2026</span> <span class="o">-</span> <span class="mi">1995</span><span class="o">;</span>
        <span class="nc">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">"Java yaklaşık "</span> <span class="o">+</span> <span class="n">javaYasi</span> <span class="o">+</span> <span class="s">" yaşında!"</span><span class="o">);</span>
    <span class="o">}</span>
<span class="o">}</span>
</code></pre></div></div>

<p>Bu sınıf şu komutla derlenir:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>javac MerhabaJVM.java
java MerhabaJVM
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">javac</code> komutu kaynak dosyadan <code class="language-plaintext highlighter-rouge">MerhabaJVM.class</code> dosyasını üretir. Bu dosya işlemciye özel makine kodu değil, JVM komutları içerir. <code class="language-plaintext highlighter-rouge">javap -c MerhabaJVM</code> komutu kullanılarak bayt kod talimatları incelenebilir.</p>

<p>Süreci matematiksel bir dönüşüm gibi gösterebiliriz:</p>

\[Kaynak\ Kod \xrightarrow{javac} Bayt\ Kod \xrightarrow{JVM} Makine\ Kodu\]

<p>Aynı <code class="language-plaintext highlighter-rouge">.class</code> dosyasının farklı sistemlerde çalışabilmesinin koşulu, her sistem için uygun bir JVM bulunmasıdır. Dolayısıyla taşınabilir olan JVM’nin kendisi değil, JVM üzerinde çalışacak şekilde üretilen bayt koddur.</p>

<h2 id="jvm-tam-olarak-ne-yapar">JVM Tam Olarak Ne Yapar?</h2>

<p><strong>Java Virtual Machine</strong>, fiziksel işlemci ile Java programı arasında soyut bir bilgisayar gibi davranır. Sınıfları yükler, bayt kodunu doğrular, belleği düzenler ve kodu çalıştırır. JVM’nin başlıca bileşenleri şunlardır:</p>

<ul>
  <li><strong>Class Loader:</strong> Gerekli sınıfları çalışma anında yükler.</li>
  <li><strong>Bytecode Verifier:</strong> Talimatların güvenli ve kurallara uygun olduğunu denetler.</li>
  <li><strong>Execution Engine:</strong> Bayt kodu yorumlar veya makine koduna dönüştürür.</li>
  <li><strong>Garbage Collector:</strong> Kullanılmayan nesnelerin belleğini otomatik olarak geri kazanır.</li>
  <li><strong>Runtime Data Areas:</strong> Heap, stack ve metot alanı gibi bellek bölgelerini yönetir.</li>
</ul>

<p>İlk JVM’ler bayt kodu çoğunlukla yorumluyordu. Modern JVM’lerdeki <strong>JIT derleyici</strong>, sık çalışan kod bölümlerini çalışma sırasında yerel makine koduna çevirir. Basitleştirilmiş performans fikri şöyle ifade edilebilir:</p>

\[T_{toplam} = T_{yükleme} + T_{JIT} + n \cdot T_{çalıştırma}\]

<p>Başlangıçta JIT maliyeti oluşsa da tekrar sayısı $n$ büyüdükçe optimize edilmiş kod önemli hız kazandırır.</p>

<h2 id="javanın-evrimi">Java’nın Evrimi</h2>

<p>Java zaman içinde yalnızca bir dil olmaktan çıkıp büyük bir platforma dönüştü. Java 5 generics ve annotation özelliklerini, Java 8 lambda ifadelerini ve Stream API’yi getirdi. Java 9 modül sistemini tanıttı; sonraki sürümler record, sealed class, pattern matching ve virtual thread gibi modern yetenekler ekledi.</p>

<p>Bugün Java’nın gücü; olgun kütüphane ekosistemi, geriye dönük uyumluluk yaklaşımı ve JVM’nin gelişmiş optimizasyonlarında yatıyor. Üstelik Kotlin, Scala ve Clojure gibi diller de JVM üzerinde çalışabiliyor. Kısacası Oak’ın küçük cihazlar için filizlenen fikri, milyonlarca uygulamayı taşıyan oldukça büyük bir ormana dönüştü.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="java" /><category term="jvm" /><category term="bayt-kod" /><category term="programlama-tarihi" /><category term="sanal-makine" /><category term="nesne-yönelimli-programlama" /><summary type="html"><![CDATA[Java, bugün kurumsal uygulamalardan Android ekosistemine kadar pek çok alanda karşımıza çıksa da yolculuğuna web için değil, etkileşimli elektronik cihazlar için başladı. Dilin asıl başarısı yalnızca sözdiziminden kaynaklanmadı; farklı donanımlarda aynı programı çalıştırmayı hedefleyen taşınabilir mimarisi, yazılım dünyasının önemli problemlerinden birine güçlü bir cevap verdi.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/java-tarihcesi-ve-53.png" /><media:content medium="image" url="https://program.sonsuz.us/img/java-tarihcesi-ve-53.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">Java’da enum, Autoboxing ve Anotasyonlar: Tip Sisteminin Güçlü Üçlüsü</title><link href="https://program.sonsuz.us/posts/javada-enum-autoboxing-ve-anotasyonlar-tip-sisteminin-guclu-uclusu/" rel="alternate" type="text/html" title="Java’da enum, Autoboxing ve Anotasyonlar: Tip Sisteminin Güçlü Üçlüsü" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/javada-enum-autoboxing-ve-anotasyonlar-tip-sisteminin-guclu-uclusu</id><content type="html" xml:base="https://program.sonsuz.us/posts/javada-enum-autoboxing-ve-anotasyonlar-tip-sisteminin-guclu-uclusu/"><![CDATA[<p>Java yalnızca sınıflardan ve metotlardan ibaret değildir; dilin tip güvenliğini artıran <code class="language-plaintext highlighter-rouge">enum</code>, ilkel tiplerle nesneler arasında köprü kuran autoboxing ve koda metadata ekleyen anotasyonlar da önemli oyunculardır. Bu üç yapı doğru kullanıldığında kod daha okunabilir, güvenli ve otomasyona uygun hâle gelir. Yanlış kullanıldıklarında ise özellikle <code class="language-plaintext highlighter-rouge">null</code>, karşılaştırma ve reflection kaynaklı küçük sürprizler hazırlayabilirler.</p>

<p>``</p>

<h2 id="güçlü-numaralandırmalar-enum">Güçlü numaralandırmalar: enum</h2>

<p>Bir değer yalnızca belirli seçeneklerden biri olabiliyorsa <code class="language-plaintext highlighter-rouge">String</code> veya rastgele sayılar yerine <code class="language-plaintext highlighter-rouge">enum</code> kullanmak daha güvenlidir. Örneğin sipariş durumunu <code class="language-plaintext highlighter-rouge">"HAZIRLANIYOR"</code> şeklinde saklamak yazım hatalarına açıktır. <code class="language-plaintext highlighter-rouge">enum</code> ise derleyicinin kontrol edebildiği sınırlı bir değer kümesi oluşturur.</p>

<p>Matematiksel olarak bir enum, sonlu bir küme gibi düşünülebilir:</p>

\[Durum = \{BEKLIYOR, HAZIRLANIYOR, GONDERILDI, IPTAL\}\]

<p>Java enum’ları basit sabit listelerinden daha güçlüdür. Alan, kurucu metot ve davranış taşıyabilirler:</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kd">public</span> <span class="kd">enum</span> <span class="nc">SiparisDurumu</span> <span class="o">{</span>
    <span class="no">BEKLIYOR</span><span class="o">(</span><span class="s">"Sipariş sırada"</span><span class="o">,</span> <span class="kc">false</span><span class="o">),</span>
    <span class="no">HAZIRLANIYOR</span><span class="o">(</span><span class="s">"Mutfak çalışıyor"</span><span class="o">,</span> <span class="kc">false</span><span class="o">),</span>
    <span class="no">GONDERILDI</span><span class="o">(</span><span class="s">"Kurye yolda"</span><span class="o">,</span> <span class="kc">true</span><span class="o">),</span>
    <span class="no">IPTAL</span><span class="o">(</span><span class="s">"Sipariş iptal edildi"</span><span class="o">,</span> <span class="kc">true</span><span class="o">);</span>

    <span class="kd">private</span> <span class="kd">final</span> <span class="nc">String</span> <span class="n">aciklama</span><span class="o">;</span>
    <span class="kd">private</span> <span class="kd">final</span> <span class="kt">boolean</span> <span class="n">sonDurum</span><span class="o">;</span>

    <span class="nc">SiparisDurumu</span><span class="o">(</span><span class="nc">String</span> <span class="n">aciklama</span><span class="o">,</span> <span class="kt">boolean</span> <span class="n">sonDurum</span><span class="o">)</span> <span class="o">{</span>
        <span class="k">this</span><span class="o">.</span><span class="na">aciklama</span> <span class="o">=</span> <span class="n">aciklama</span><span class="o">;</span>
        <span class="k">this</span><span class="o">.</span><span class="na">sonDurum</span> <span class="o">=</span> <span class="n">sonDurum</span><span class="o">;</span>
    <span class="o">}</span>

    <span class="kd">public</span> <span class="nc">String</span> <span class="nf">getAciklama</span><span class="o">()</span> <span class="o">{</span>
        <span class="k">return</span> <span class="n">aciklama</span><span class="o">;</span>
    <span class="o">}</span>

    <span class="kd">public</span> <span class="kt">boolean</span> <span class="nf">isSonDurum</span><span class="o">()</span> <span class="o">{</span>
        <span class="k">return</span> <span class="n">sonDurum</span><span class="o">;</span>
    <span class="o">}</span>
<span class="o">}</span>
</code></pre></div></div>

<p>Bu örnek, durumla ilgili veriyi farklı <code class="language-plaintext highlighter-rouge">if</code> bloklarına dağıtmak yerine doğrudan enum içinde toplar. Enum değerleri tekil nesneler olduğundan <code class="language-plaintext highlighter-rouge">==</code> ile güvenle karşılaştırılabilir. Dış sistemlerden gelen metinleri <code class="language-plaintext highlighter-rouge">valueOf()</code> ile dönüştürürken geçersiz değerlerin <code class="language-plaintext highlighter-rouge">IllegalArgumentException</code> üreteceği unutulmamalıdır.</p>

<table>
  <thead>
    <tr>
      <th>Yaklaşım</th>
      <th style="text-align: right">Tip güvenliği</th>
      <th style="text-align: right">Davranış taşıma</th>
      <th style="text-align: right">Yazım hatası riski</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">String</code> sabitleri</td>
      <td style="text-align: right">Düşük</td>
      <td style="text-align: right">Hayır</td>
      <td style="text-align: right">Yüksek</td>
    </tr>
    <tr>
      <td>Sayısal sabitler</td>
      <td style="text-align: right">Düşük</td>
      <td style="text-align: right">Hayır</td>
      <td style="text-align: right">Orta</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">enum</code></td>
      <td style="text-align: right">Yüksek</td>
      <td style="text-align: right">Evet</td>
      <td style="text-align: right">Düşük</td>
    </tr>
  </tbody>
</table>

<p><img src="/img/javada-enum-autoboxing-17.svg" alt="javada-enum-autoboxing-17" /></p>

<h2 id="autoboxing-ve-unboxing">Autoboxing ve unboxing</h2>

<p>Java’nın <code class="language-plaintext highlighter-rouge">int</code>, <code class="language-plaintext highlighter-rouge">double</code> ve <code class="language-plaintext highlighter-rouge">boolean</code> gibi ilkel tipleri nesne değildir. Koleksiyonlar ise nesne bekler. Autoboxing, ilkel değeri karşılık gelen sarmalayıcı sınıfa otomatik dönüştürür; unboxing bunun tersidir.</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nc">List</span><span class="o">&lt;</span><span class="nc">Integer</span><span class="o">&gt;</span> <span class="n">puanlar</span> <span class="o">=</span> <span class="k">new</span> <span class="nc">ArrayList</span><span class="o">&lt;&gt;();</span>
<span class="n">puanlar</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">90</span><span class="o">);</span>          <span class="c1">// int -&gt; Integer: autoboxing</span>
<span class="kt">int</span> <span class="n">ilkPuan</span> <span class="o">=</span> <span class="n">puanlar</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">);</span> <span class="c1">// Integer -&gt; int: unboxing</span>
</code></pre></div></div>

<p>Derleyici zihninde yaklaşık olarak şu dönüşüm gerçekleşir:</p>

<p>\(int \xrightarrow{boxing} Integer\)
\(Integer \xrightarrow{unboxing} int\)</p>

<table>
  <thead>
    <tr>
      <th>İlkel tip</th>
      <th>Sarmalayıcı sınıf</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">int</code></td>
      <td><code class="language-plaintext highlighter-rouge">Integer</code></td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">long</code></td>
      <td><code class="language-plaintext highlighter-rouge">Long</code></td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">double</code></td>
      <td><code class="language-plaintext highlighter-rouge">Double</code></td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">boolean</code></td>
      <td><code class="language-plaintext highlighter-rouge">Boolean</code></td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">char</code></td>
      <td><code class="language-plaintext highlighter-rouge">Character</code></td>
    </tr>
  </tbody>
</table>

<p>Kolaylık güzel olsa da <code class="language-plaintext highlighter-rouge">null</code> değer unboxing sırasında <code class="language-plaintext highlighter-rouge">NullPointerException</code> üretir:</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nc">Integer</span> <span class="n">adet</span> <span class="o">=</span> <span class="kc">null</span><span class="o">;</span>
<span class="c1">// int toplam = adet + 1; // Unboxing sırasında hata oluşur</span>
</code></pre></div></div>

<p>Ayrıca <code class="language-plaintext highlighter-rouge">Integer</code> nesnelerini <code class="language-plaintext highlighter-rouge">==</code> ile karşılaştırmak tehlikelidir. Java bazı küçük sayıları önbelleğe aldığı için sonuçlar şaşırtıcı olabilir. Değer karşılaştırmasında <code class="language-plaintext highlighter-rouge">equals()</code> kullanılmalıdır. Yoğun döngülerde gereksiz boxing işlemleri ek nesne maliyeti de oluşturabilir.</p>

<h2 id="anotasyonlar-kodun-üzerine-iliştirilen-metadata">Anotasyonlar: Kodun üzerine iliştirilen metadata</h2>

<p>Anotasyonlar doğrudan iş mantığını çalıştırmaz; derleyiciye, araçlara veya çalışma zamanı kütüphanelerine ek bilgi verir. <code class="language-plaintext highlighter-rouge">@Override</code>, metodun üst sınıftaki bir metodu ezdiğini doğrulatır. Spring’deki <code class="language-plaintext highlighter-rouge">@Service</code> veya JPA’deki <code class="language-plaintext highlighter-rouge">@Entity</code> ise framework davranışlarını yönlendirir.</p>

<p>Kendi anotasyonumuzu da oluşturabiliriz:</p>

<div class="language-java highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nd">@Retention</span><span class="o">(</span><span class="nc">RetentionPolicy</span><span class="o">.</span><span class="na">RUNTIME</span><span class="o">)</span>
<span class="nd">@Target</span><span class="o">(</span><span class="nc">ElementType</span><span class="o">.</span><span class="na">METHOD</span><span class="o">)</span>
<span class="kd">public</span> <span class="nd">@interface</span> <span class="nc">YetkiGerekli</span> <span class="o">{</span>
    <span class="nc">String</span> <span class="nf">rol</span><span class="o">();</span>
<span class="o">}</span>
</code></pre></div></div>

<p>Buradaki <code class="language-plaintext highlighter-rouge">@Retention</code>, bilginin çalışma zamanına kadar korunacağını; <code class="language-plaintext highlighter-rouge">@Target</code> ise yalnızca metotlarda kullanılabileceğini belirtir. Ardından <code class="language-plaintext highlighter-rouge">@YetkiGerekli(rol = "ADMIN")</code> biçiminde işaretlenen metotlar reflection ile bulunabilir ve çağrıdan önce yetki kontrolü yapılabilir.</p>

<table>
  <thead>
    <tr>
      <th>Saklama politikası</th>
      <th>Ne zamana kadar yaşar?</th>
      <th>Yaygın amaç</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">SOURCE</code></td>
      <td>Derleme öncesi</td>
      <td>Kod üretimi, analiz</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">CLASS</code></td>
      <td>Bytecode içinde</td>
      <td>Araç desteği</td>
    </tr>
    <tr>
      <td><code class="language-plaintext highlighter-rouge">RUNTIME</code></td>
      <td>Çalışma zamanı</td>
      <td>Reflection, framework</td>
    </tr>
  </tbody>
</table>

<p>Özetle enum değer alanını sınırlar, autoboxing ilkel ve nesne dünyalarını yakınlaştırır, anotasyonlar ise kod hakkında kod dışı bilgi taşır. Üçü birlikte kullanıldığında Java uygulamaları daha açıklayıcı, denetlenebilir ve framework dostu olur.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="java" /><category term="enum" /><category term="autoboxing" /><category term="anotasyon" /><category term="metadata" /><category term="reflection" /><summary type="html"><![CDATA[Java yalnızca sınıflardan ve metotlardan ibaret değildir; dilin tip güvenliğini artıran enum, ilkel tiplerle nesneler arasında köprü kuran autoboxing ve koda metadata ekleyen anotasyonlar da önemli oyunculardır. Bu üç yapı doğru kullanıldığında kod daha okunabilir, güvenli ve otomasyona uygun hâle gelir. Yanlış kullanıldıklarında ise özellikle null, karşılaştırma ve reflection kaynaklı küçük sürprizler hazırlayabilirler.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/javada-enum-autoboxing-17.png" /><media:content medium="image" url="https://program.sonsuz.us/img/javada-enum-autoboxing-17.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">PATH Sırası: Terminal Hangi Komutu Çalıştırıyor?</title><link href="https://program.sonsuz.us/posts/path-sirasi-terminal-hangi-komutu-calistiriyor/" rel="alternate" type="text/html" title="PATH Sırası: Terminal Hangi Komutu Çalıştırıyor?" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/path-sirasi-terminal-hangi-komutu-calistiriyor</id><content type="html" xml:base="https://program.sonsuz.us/posts/path-sirasi-terminal-hangi-komutu-calistiriyor/"><![CDATA[<p>Terminale <code class="language-plaintext highlighter-rouge">python</code>, <code class="language-plaintext highlighter-rouge">node</code> veya <code class="language-plaintext highlighter-rouge">git</code> yazdığınızda kabuk, bu programın nerede olduğunu sihirli biçimde bilmez. Bunun yerine <code class="language-plaintext highlighter-rouge">PATH</code> adlı ortam değişkenindeki dizinleri soldan sağa tarar ve eşleşen ilk çalıştırılabilir dosyayı seçer. Dolayısıyla aynı isimli iki komuttan hangisinin çalışacağı, çoğu zaman sürüm numarasından değil dizinlerin sırasından kaynaklanır.
``</p>
<h2 id="path-tam-olarak-nedir">PATH tam olarak nedir?</h2>

<p><code class="language-plaintext highlighter-rouge">PATH</code>, çalıştırılabilir dosyaların aranacağı dizinleri tutan bir listedir. Linux ve macOS sistemlerinde dizinler <code class="language-plaintext highlighter-rouge">:</code> karakteriyle ayrılır:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">printf</span> <span class="s1">'%s\n'</span> <span class="s2">"</span><span class="nv">$PATH</span><span class="s2">"</span>
</code></pre></div></div>

<p>Örnek bir çıktı şöyle olabilir:</p>

<div class="language-text highlighter-rouge"><div class="highlight"><pre class="highlight"><code>/home/ada/bin:/usr/local/bin:/usr/bin:/bin
</code></pre></div></div>

<p>Kabuk, <code class="language-plaintext highlighter-rouge">ornek</code> komutu girildiğinde önce <code class="language-plaintext highlighter-rouge">/home/ada/bin/ornek</code>, sonra <code class="language-plaintext highlighter-rouge">/usr/local/bin/ornek</code> ve devamında diğer olasılıkları kontrol eder. İlk uygun dosya bulunduğunda arama sona erer.</p>

<p>Bunu matematiksel olarak $PATH = (d_1, d_2, \ldots, d_n)$ biçiminde sıralı bir dizi kabul ederek düşünebiliriz. Çalıştırılan dosyanın indeksi:</p>

\[k = \min\{i \mid d_i/komut \text{ çalıştırılabilir durumdadır}\}\]

<p>Buradaki <code class="language-plaintext highlighter-rouge">min</code>, neden sıranın kritik olduğunu anlatır: İlk eşleşme kazanır; sonraki dosyalar daha yeni veya daha doğru olsa bile dikkate alınmaz.</p>

<p>\vert  PATH sırası \vert  Seçilen komut \vert  Olası sonuç \vert 
\vert —\vert —\vert —\vert 
\vert  <code class="language-plaintext highlighter-rouge">/usr/local/bin:/usr/bin</code> \vert  <code class="language-plaintext highlighter-rouge">/usr/local/bin/python</code> \vert  Elle kurulan sürüm çalışabilir \vert 
\vert  <code class="language-plaintext highlighter-rouge">/usr/bin:/usr/local/bin</code> \vert  <code class="language-plaintext highlighter-rouge">/usr/bin/python</code> \vert  Sistem sürümü çalışabilir \vert 
\vert  <code class="language-plaintext highlighter-rouge">./bin:/usr/bin</code> \vert  Projedeki komut \vert  Projeye özel araç öne geçer \vert</p>

<h2 id="hangi-dosyanın-çalıştığını-bulmak">Hangi dosyanın çalıştığını bulmak</h2>

<p>Bir komutun çözümlendiği ilk yolu görmek için <code class="language-plaintext highlighter-rouge">command -v</code> kullanılabilir:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">command</span> <span class="nt">-v</span> python
<span class="nb">command</span> <span class="nt">-v</span> git
</code></pre></div></div>

<p>Aynı ada sahip bütün adayları görmek için Bash ve Zsh üzerinde <code class="language-plaintext highlighter-rouge">type -a</code> oldukça kullanışlıdır:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">type</span> <span class="nt">-a</span> python
</code></pre></div></div>

<p>Örneğin çıktı hem <code class="language-plaintext highlighter-rouge">/home/ada/bin/python</code> hem de <code class="language-plaintext highlighter-rouge">/usr/bin/python</code> gösteriyorsa terminal yalnızca ilkini çalıştırır. Belirli dosyayı kesin olarak kullanmak istediğinizde tam yol vermek arama mekanizmasını devre dışı bırakır:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>/usr/bin/python <span class="nt">--version</span>
</code></pre></div></div>

<p>\vert  Yöntem \vert  PATH araması yapar mı? \vert  Kullanım amacı \vert 
\vert —\vert —:\vert —\vert 
\vert  <code class="language-plaintext highlighter-rouge">python</code> \vert  Evet \vert  Normal komut çağrısı \vert 
\vert  <code class="language-plaintext highlighter-rouge">/usr/bin/python</code> \vert  Hayır \vert  Kesin dosyayı çalıştırma \vert 
\vert  <code class="language-plaintext highlighter-rouge">command -v python</code> \vert  Arama sonucunu gösterir \vert  Tanılama \vert 
\vert  <code class="language-plaintext highlighter-rouge">type -a python</code> \vert  Tüm eşleşmeleri gösterir \vert  Çakışma inceleme \vert</p>

<h2 id="sırayı-bilinçli-olarak-değiştirmek">Sırayı bilinçli olarak değiştirmek</h2>

<p>Kullanıcıya özel araçları öne almak için dizin listenin başına eklenebilir:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">export </span><span class="nv">PATH</span><span class="o">=</span><span class="s2">"</span><span class="nv">$HOME</span><span class="s2">/bin:</span><span class="nv">$PATH</span><span class="s2">"</span>
</code></pre></div></div>

<p>Bu komut mevcut <code class="language-plaintext highlighter-rouge">PATH</code> değerini korur, fakat <code class="language-plaintext highlighter-rouge">$HOME/bin</code> dizinine öncelik verir. Değişikliğin kalıcı olması için satır genellikle <code class="language-plaintext highlighter-rouge">~/.bashrc</code>, <code class="language-plaintext highlighter-rouge">~/.zshrc</code> veya kullanılan kabuğun ilgili yapılandırma dosyasına eklenir. Sona eklemek ise sistem araçlarına öncelik tanır:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">export </span><span class="nv">PATH</span><span class="o">=</span><span class="s2">"</span><span class="nv">$PATH</span><span class="s2">:</span><span class="nv">$HOME</span><span class="s2">/bin"</span>
</code></pre></div></div>

<p>Bazı kabuklar daha önce buldukları yolları önbelleğe alabilir. Bir dosyayı taşıdıktan sonra hâlâ eski komut çalışıyorsa Bash üzerinde önbelleği temizlemek mümkündür:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">hash</span> <span class="nt">-r</span>
</code></pre></div></div>

<h2 id="güvenlik-tarafı-noktaya-dikkat">Güvenlik tarafı: Noktaya dikkat</h2>

<p>Geçerli dizini temsil eden <code class="language-plaintext highlighter-rouge">.</code> değerini PATH’in başına koymak risklidir:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">export </span><span class="nv">PATH</span><span class="o">=</span><span class="s2">".:</span><span class="nv">$PATH</span><span class="s2">"</span>
</code></pre></div></div>

<p>İçinde zararlı bir <code class="language-plaintext highlighter-rouge">ls</code> dosyası bulunan klasöre girildiğinde gerçek <code class="language-plaintext highlighter-rouge">/bin/ls</code> yerine bu dosya çalışabilir. Bu nedenle <code class="language-plaintext highlighter-rouge">.</code> mümkünse PATH’e hiç eklenmemeli; gerekiyorsa yerel program açıkça <code class="language-plaintext highlighter-rouge">./program</code> şeklinde çağrılmalıdır.</p>

<p>Özetle PATH yalnızca bir dizin listesi değil, bir öncelik sistemidir. Beklenmeyen sürüm çalıştığında önce <code class="language-plaintext highlighter-rouge">command -v</code>, ardından <code class="language-plaintext highlighter-rouge">type -a</code> kullanın; sırayı inceleyin ve gerekirse tam dosya yoluyla doğrulama yapın. Terminal gizemli davranmıyordur—yalnızca listeyi soldan sağa okumaktadır.</p>

<p><img src="/img/path-sirasi-terminal-76.svg" alt="path-sirasi-terminal-76" /></p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="shell" /><category term="path" /><category term="linux" /><category term="terminal" /><category term="komut-satırı" /><category term="güvenlik" /><summary type="html"><![CDATA[Terminale python, node veya git yazdığınızda kabuk, bu programın nerede olduğunu sihirli biçimde bilmez. Bunun yerine PATH adlı ortam değişkenindeki dizinleri soldan sağa tarar ve eşleşen ilk çalıştırılabilir dosyayı seçer. Dolayısıyla aynı isimli iki komuttan hangisinin çalışacağı, çoğu zaman sürüm numarasından değil dizinlerin sırasından kaynaklanır.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/path-sirasi-terminal-76.png" /><media:content medium="image" url="https://program.sonsuz.us/img/path-sirasi-terminal-76.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry><entry><title type="html">Python dict Sırası: Python 3.7 Öncesi Kodlarda Gizli Uyumluluk Tuzağı</title><link href="https://program.sonsuz.us/posts/python-dict-sirasi-python-37-oncesi-kodlarda-gizli-uyumluluk-tuzagi/" rel="alternate" type="text/html" title="Python dict Sırası: Python 3.7 Öncesi Kodlarda Gizli Uyumluluk Tuzağı" /><published>2026-10-18T00:00:00+00:00</published><updated>2026-10-18T00:00:00+00:00</updated><id>https://program.sonsuz.us/posts/python-dict-sirasi-python-37-oncesi-kodlarda-gizli-uyumluluk-tuzagi</id><content type="html" xml:base="https://program.sonsuz.us/posts/python-dict-sirasi-python-37-oncesi-kodlarda-gizli-uyumluluk-tuzagi/"><![CDATA[<p><img src="/img/python-dict-sirasi-46.svg" alt="python-dict-sirasi-46" /></p>

<p>Python sözlükleri bugün anahtarları eklenme sırasına göre dolaştığı için oldukça öngörülebilir davranıyor. Ancak eski bir Python sürümünde çalışan projeyi ayağa kaldırdığınızda aynı kodun farklı sırada çıktı üretmesi mümkündür. Bu durum yalnızca estetik bir farklılık değildir; testleri, dosya üretimini, API yanıtlarını ve hatta uygulama mantığını bozabilen sinsi bir uyumluluk problemidir.
``</p>
<h2 id="sırasız-tam-olarak-ne-demekti">“Sırasız” tam olarak ne demekti?</h2>

<p>Bir <code class="language-plaintext highlighter-rouge">dict</code>, anahtarları değerlere bağlayan hash tablosu tabanlı bir veri yapısıdır. Bir anahtarın yerleşimi kabaca şu ilişkiyle düşünülebilir:</p>

\[index = hash(key) \bmod N\]

<p>Buradaki $N$, tablonun kapasitesini temsil eder. Python 3.7 öncesinde sözlüğün dolaşım sırası, anahtarların eklenme zamanından ziyade hash değerleri, tablonun boyutu ve yeniden boyutlandırma işlemleri gibi ayrıntılardan etkilenebilirdi.</p>

<p>“Sırasız” ifadesi, öğelerin her erişimde mutlaka rastgele dizildiği anlamına gelmez. Asıl anlamı, programcının gözlemlediği sıranın dil tarafından <strong>garanti edilmemesidir</strong>. Aynı makinede kararlı görünen bir çıktı, başka Python sürümünde veya farklı bir süreçte değişebilirdi. Hash randomization özelliği de özellikle metin anahtarlarında süreçler arasında farklılık oluşturabilir.</p>

<table>
  <thead>
    <tr>
      <th>Sürüm</th>
      <th><code class="language-plaintext highlighter-rouge">dict</code> sırası</th>
      <th>Güvenilebilir mi?</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Python 3.5 ve öncesi</td>
      <td>Belirli olmayan sıra</td>
      <td>Hayır</td>
    </tr>
    <tr>
      <td>CPython 3.6</td>
      <td>Eklenme sırası pratikte korunur</td>
      <td>Dil garantisi değildir</td>
    </tr>
    <tr>
      <td>Python 3.7 ve sonrası</td>
      <td>Eklenme sırası korunur</td>
      <td>Evet</td>
    </tr>
    <tr>
      <td>Eski sürümlerde <code class="language-plaintext highlighter-rouge">OrderedDict</code></td>
      <td>Eklenme sırası korunur</td>
      <td>Evet</td>
    </tr>
  </tbody>
</table>

<p>CPython 3.6’da sıralı davranış, daha kompakt sözlük uygulamasının bir sonucu olarak ortaya çıktı. Python 3.7 ile bu davranış resmi dil özelliği hâline geldi.</p>

<h2 id="eski-kod-nasıl-bozulur">Eski kod nasıl bozulur?</h2>

<p>Aşağıdaki kod modern Python’da <code class="language-plaintext highlighter-rouge">host</code>, <code class="language-plaintext highlighter-rouge">port</code>, <code class="language-plaintext highlighter-rouge">debug</code> sırasını korur:</p>

<div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">config</span> <span class="o">=</span> <span class="p">{}</span>
<span class="n">config</span><span class="p">[</span><span class="sh">"</span><span class="s">host</span><span class="sh">"</span><span class="p">]</span> <span class="o">=</span> <span class="sh">"</span><span class="s">localhost</span><span class="sh">"</span>
<span class="n">config</span><span class="p">[</span><span class="sh">"</span><span class="s">port</span><span class="sh">"</span><span class="p">]</span> <span class="o">=</span> <span class="mi">8000</span>
<span class="n">config</span><span class="p">[</span><span class="sh">"</span><span class="s">debug</span><span class="sh">"</span><span class="p">]</span> <span class="o">=</span> <span class="bp">True</span>

<span class="n">line</span> <span class="o">=</span> <span class="sh">"</span><span class="s">;</span><span class="sh">"</span><span class="p">.</span><span class="nf">join</span><span class="p">(</span><span class="sa">f</span><span class="sh">"</span><span class="si">{</span><span class="n">key</span><span class="si">}</span><span class="s">=</span><span class="si">{</span><span class="n">value</span><span class="si">}</span><span class="sh">"</span> <span class="k">for</span> <span class="n">key</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">config</span><span class="p">.</span><span class="nf">items</span><span class="p">())</span>
<span class="nf">print</span><span class="p">(</span><span class="n">line</span><span class="p">)</span>
</code></pre></div></div>

<p>Kod, yapılandırmayı tek satırlık bir metne dönüştürür. Python 3.7 ve sonrasında sonuç öngörülebilirken eski sürümlerde alanlar farklı sırada gelebilir. Bu metin bir snapshot testiyle karşılaştırılıyorsa test başarısız olur. Daha kötüsü, sıralamaya duyarlı eski bir tüketici varsa veri yanlış yorumlanabilir.</p>

<p>Benzer riskler şuralarda görülür:</p>

<ul>
  <li>JSON veya CSV benzeri çıktıların metinsel olarak karşılaştırılması,</li>
  <li>HTML şablonlarında alanların beklenen sırada gösterilmesi,</li>
  <li>Komut satırı argümanlarının sözlükten üretilmesi,</li>
  <li>Sözlük anahtarlarının indeks gibi kullanılması,</li>
  <li>Snapshot ve golden file testleri.</li>
</ul>

<p>Teorik olarak bir eşlemenin doğruluğu sıra üzerinden değil, anahtar-değer çiftleri üzerinden tanımlanmalıdır:</p>

\[D_1 = D_2 \iff \forall k,\ D_1[k] = D_2[k]\]

<p>Yani iki sözlük aynı çiftlere sahipse dolaşım sıraları farklı olsa bile eşit kabul edilir.</p>

<h2 id="güvenli-uyumluluk-yöntemleri">Güvenli uyumluluk yöntemleri</h2>

<p>Sıra iş mantığının parçasıysa eski sürümlerde <code class="language-plaintext highlighter-rouge">OrderedDict</code> kullanılmalıdır:</p>

<div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kn">from</span> <span class="n">collections</span> <span class="kn">import</span> <span class="n">OrderedDict</span>

<span class="n">config</span> <span class="o">=</span> <span class="nc">OrderedDict</span><span class="p">([</span>
    <span class="p">(</span><span class="sh">"</span><span class="s">host</span><span class="sh">"</span><span class="p">,</span> <span class="sh">"</span><span class="s">localhost</span><span class="sh">"</span><span class="p">),</span>
    <span class="p">(</span><span class="sh">"</span><span class="s">port</span><span class="sh">"</span><span class="p">,</span> <span class="mi">8000</span><span class="p">),</span>
    <span class="p">(</span><span class="sh">"</span><span class="s">debug</span><span class="sh">"</span><span class="p">,</span> <span class="bp">True</span><span class="p">),</span>
<span class="p">])</span>

<span class="k">for</span> <span class="n">key</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">config</span><span class="p">.</span><span class="nf">items</span><span class="p">():</span>
    <span class="nf">print</span><span class="p">(</span><span class="n">key</span><span class="p">,</span> <span class="n">value</span><span class="p">)</span>
</code></pre></div></div>

<p>Amaç yalnızca deterministik çıktıysa anahtarları açıkça sıralamak daha net olabilir:</p>

<div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">for</span> <span class="n">key</span> <span class="ow">in</span> <span class="nf">sorted</span><span class="p">(</span><span class="n">config</span><span class="p">):</span>
    <span class="nf">print</span><span class="p">(</span><span class="sa">f</span><span class="sh">"</span><span class="si">{</span><span class="n">key</span><span class="si">}</span><span class="s">=</span><span class="si">{</span><span class="n">config</span><span class="p">[</span><span class="n">key</span><span class="p">]</span><span class="si">}</span><span class="sh">"</span><span class="p">)</span>
</code></pre></div></div>

<table>
  <thead>
    <tr>
      <th>İhtiyaç</th>
      <th>Tercih</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Eklenme sırasını korumak</td>
      <td><code class="language-plaintext highlighter-rouge">OrderedDict</code> veya Python 3.7+</td>
    </tr>
    <tr>
      <td>Alfabetik çıktı üretmek</td>
      <td><code class="language-plaintext highlighter-rouge">sorted(dict)</code></td>
    </tr>
    <tr>
      <td>Yalnızca içerik karşılaştırmak</td>
      <td>Doğrudan sözlük eşitliği</td>
    </tr>
    <tr>
      <td>Çok sürümlü kütüphane geliştirmek</td>
      <td>Desteklenen en eski sürümde test</td>
    </tr>
  </tbody>
</table>

<p>Sonuç olarak modern <code class="language-plaintext highlighter-rouge">dict</code> davranışını geçmişe doğru varsaymak tehlikelidir. Legacy kod incelerken <code class="language-plaintext highlighter-rouge">items()</code>, <code class="language-plaintext highlighter-rouge">keys()</code> ve sözlük üzerinde doğrudan dönen her döngüye dikkat etmek gerekir. Sıra önemliyse bunu açıkça ifade etmek, Python’un tarihsel davranışlarına güvenmekten çok daha sağlamdır.</p>]]></content><author><name>Sonsuz Us</name></author><category term="Bilgi" /><category term="python" /><category term="dict" /><category term="geriye-dönük-uyumluluk" /><category term="veri-yapıları" /><category term="legacy-kod" /><category term="python-3" /><summary type="html"><![CDATA[Python sözlükleri bugün anahtarları eklenme sırasına göre dolaştığı için oldukça öngörülebilir davranıyor. Ancak eski bir Python sürümünde çalışan projeyi ayağa kaldırdığınızda aynı kodun farklı sırada çıktı üretmesi mümkündür. Bu durum yalnızca estetik bir farklılık değildir; testleri, dosya üretimini, API yanıtlarını ve hatta uygulama mantığını bozabilen sinsi bir uyumluluk problemidir.]]></summary><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://program.sonsuz.us/img/python-dict-sirasi-46.png" /><media:content medium="image" url="https://program.sonsuz.us/img/python-dict-sirasi-46.png" xmlns:media="http://search.yahoo.com/mrss/" /></entry></feed>