---
title: 'Değişkenler ve Sabitler'
source: 'https://academia.sh/tr/kurslar/ruby-temelleri/degiskenler-ve-sabitler'
course: 'Ruby Temelleri'
language: tr
updated: '2026-10-21T05:03:43+00:00'
license: 'CC BY-SA 4.0'
objectives:
    - 'Yerel değişken, örnek değişkeni, genel değişken ve sabiti kapsam işaretleriyle ayırt eder'
    - 'Atamayı defined? ile ölçerek bir ileti değil sözdizimi olduğunu gösterir'
    - 'Birleşik atamanın (+=, ||=) atama, içindeki toplamanın ise ileti olduğunu ayırır'
---

# Değişkenler ve Sabitler

Ruby'de atamanın bir ileti değil sözdizimi olması; yerel değişken, örnek değişkeni, genel değişken ve sabitin ad işaretiyle ayrılması; defined? ile ölçülen sınırlar.

Önceki ders her değerin bir sınıfa ait bir nesne olduğunu ve iletiyi alıcının sınıfının yanıtladığını kurdu. Bir ad bu nesnelerden birine nasıl bağlanıyor sorusu açık kaldı: `x = 5` yazıldığında `x`'e bir ileti mi gidiyor, `5`'e mi, yoksa ortada hiç ileti yok mu? Değişken kavramının kendisi Programlama Temelleri kursunda (M01/K02) anlatılmıştı; burada o kavram tekrarlanmaz. Bu ders yalnız Ruby'ye özgü soruyu ölçer: ad nesneye bağlanırken kim çalışır?

Ruby'de bir adın ne olduğunu başındaki işaret belirler. Bu işaretlere kapsam işareti diyoruz: işaretsiz küçük harfle başlayan ad yerel değişkendir, `@` ile başlayan örnek değişkeni, `$` ile başlayan genel değişken, büyük harfle başlayan ad sabittir. `@@` ile başlayan sınıf değişkeni de vardır; ona Kapsam Sınırları ve Paralel Atama bölümünde dönülür. Aşağıdaki dosya dört işareti, tanımsız bir sabiti ve bir atamayı `defined?` ile ayrı ayrı sorgular.

## Ad İşareti Türü Belirler

`defined?` bir ifadeyi çalıştırmadan onun ne olduğunu söyleyen bir deyimdir. Tanımsız bir ad için `nil` döndürür, tanımlı için ne olduğunu belirten bir dizgi. Bu, derste kullanacağımız ölçü aletidir.

```ruby
# kapsam_isaretleri.rb — ad isareti degiskenin turunu belirler
x = 5
@a = 1
$gz = 2

puts defined?(x)
puts defined?(@a)
puts defined?($gz)
puts defined?(String)
p defined?(Yok)
puts defined?(sonuc = 5)
```

```
local-variable
instance-variable
global-variable
constant
nil
assignment
```

Altı sorgu, altı farklı yanıt: `x` yerel değişken, `@a` örnek değişkeni, `$gz` genel değişken, `String` sabit. Tanımsız sabit `Yok` için `nil` döndü. Son satır asıl konudur: `sonuc = 5` ifadesi `"assignment"` olarak bildirildi. Ne `"method"` ne `"expression"`; atamanın kendi adı var.

**DT7.** Bu derste "atama" `=` ile bir adı bir nesneye bağlayan yazımdır. `defined?` yalnız ifadenin türünü okur, atamayı gerçekten çalıştırmaz; bu yüzden yukarıdaki `sonuc` adı hiç oluşmadı. Sabit adlarına yeniden atamanın uyarı bastığı bilinir, ama o uyarı bir dosya yolu taşıdığı için burada basılmaz ve ölçülmez; yalnız düzyazıda anılır.

## Sabit Adı Bağlar, Nesneyi Dondurmaz

Büyük harfle başlayan bir ad sabittir. Sabitin tanımlı olduğu `Object.const_get` ile okunabilir. Peki sabit neyi sabitler: adın bağlandığı nesneyi mi, adın bağlanmasını mı? Aşağıdaki dosya bir sayıyı ve bir diziyi birer sabite bağlar, sonra diziye bir eleman ekler.

```ruby
# sabit_dizi.rb — sabit adi baglar, nesneyi dondurmaz
SINIR = 10
LISTE = [1]

puts Object.const_get(:SINIR)
puts defined?(SINIR)
LISTE << 2
p LISTE
puts LISTE.frozen?
puts SINIR.frozen?
```

```
10
constant
[1, 2]
false
true
```

Dizi `LISTE` sabitine bağlı olduğu hâlde değişti: sabit adın başka bir nesneye bağlanmasını uyarıyla işaretler, nesnenin içeriğini kilitlemez. Dizi dondurulmamıştır (`false`). Sayılar ise zaten değiştirilemez nesnelerdir ve `frozen?` onlar için `true` döner. Sabiti gerçekten değiştirilemez yapmak isteyen, nesneyi ayrıca dondurur; dondurma bu kursta Semboller ve Dizgiler dersinde dizgiler üzerinde ölçülür.

## Her Tür Kendi Yerinde Tutulur

Kapsam işaretleri yalnız yazım kolaylığı değildir; her tür farklı bir yerde saklanır. Yerel değişkenler çalışan kodun kendi kapsamındadır, örnek değişkenleri bir nesneye bağlıdır, genel değişkenler ise programın tamamında görünür. Ruby bu üçünü listeleyen yöntemler sunar. Aşağıdaki dosya üst düzeyde üç türü tanımlar ve her birini kendi listesinde arar.

```ruby
# degisken_listeleri.rb — her tur kendi listesinde tutulur
x = 5
@a = 1
$gz = 2

p local_variables
p instance_variables
puts global_variables.include?(:$gz)
puts self.inspect
puts self.class
```

```
[:x]
[:@a]
true
main
Object
```

Yerel değişken listesinde `x`, örnek değişkeni listesinde `@a` bulundu; `$gz` ise genel değişkenler listesinde. Örnek değişkeninin kimin üzerinde durduğu sorusunun cevabı `self`'tir: üst düzeyde `self` dosyanın ana nesnesidir, `main` olarak yazdırılır ve sınıfı `Object`'tir. Yani üst düzeyde yazılan `@a`, bir `Object` örneğine bağlanmıştır; örnek değişkeni her zaman bir nesnenin değişkenidir.

## Atama Bir İleti Değil

Önceki dersin kuralı şuydu: `5 + 3` bir iletidir ve yanıtlayanı sınıftır. Atama için aynı soru sorulabilir: `x = 5` bir iletiyse, onu yanıtlayan bir sahip bulunmalıdır. Aşağıdaki dosya üç şeyi yan yana koyar: düz atamayı, değer döndüren yöntem çağrısını ve atamanın dönüş değerini.

```ruby
# atama_donus.rb — atama ifadesi bir deger tasir
puts defined?(a = 1)
puts defined?(puts)
puts defined?(1 + 2)

deger = (b = 7)
puts deger
puts b
```

```
assignment
method
method
7
7
```

Üç ifade üç farklı tür verdi: atama `"assignment"`, `puts` çağrısı `"method"`, toplama `"method"`. Yani `1 + 2` ile `puts` aynı kategoridedir, `a = 1` ayrı. Atama yine de bir değer taşır: `(b = 7)` ifadesinin değeri `7`'dir ve ad olarak `b` bağlanmıştır. Bu iki gözlem birlikte atamanın bir ifade olduğunu ama bir yöntem çağrısı olmadığını söyler.

## Kapsam Sınırları ve Paralel Atama

Bu bölüm adların nerede görüldüğünü ölçer. `defined?` ifadeyi çalıştırmadan yalnız türünü bildirir; burada bir kapsam sondası olarak kullanılıyor. Eksen sözdizimidir: bir adın görünüp görünmemesini dilin kapsam kuralları belirler, bir sınıfın tanımladığı yöntem belirlemez. Üç soru soruluyor: `def` ile açılan yöntem dıştaki yerel değişkeni görür mü, blok görür mü, ve sınıf gövdesinde açılan `@@` işaretli ad hangi türdür?

```ruby
# kapsam_olcumu.rb — yontem ve blok dis yereli nasil gorur
dis = 10
def yontem_icinde
  defined?(dis).inspect
end
puts yontem_icinde
blok_sonucu = [1].map { defined?(dis) }
puts blok_sonucu.first
class Kayit
  @@adet = 0
  def self.sayac_turu
    defined?(@@adet)
  end
end
puts Kayit.sayac_turu
```

```
nil
local-variable
class variable
```

Üç ölçüm üç ayrı sonuç verdi. `def` ile açılan yöntemin içinden dıştaki `dis` yerel değişkeni sorulduğunda `defined?(dis).inspect` `nil` basıldı: yöntem gövdesi yeni bir kapsam başlatır ve dıştaki yereller içeri geçmez. Aynı ad bir blok içinden sorulduğunda `"local-variable"` döndü: blok, tanımlandığı yerin yerellerini görür. `@@adet` için sonuç `"class variable"` oldu; sınıf gövdesinde açılan bu tür, `@` ve `$` işaretlerinden ayrı bir kategoridir. Bu üç sonucun ortak noktası, hiçbirini bir ileti karşılamamasıdır: yöntemin dışarıyı görmemesi, bloğun görmesi ve `@@` işaretinin türü, hepsi dilin yazım kurallarındandır. Adın nerede tanımlandığı kadar, nerede sorulduğu da sonucu değiştirir: aynı `dis` adı iki farklı yerden sorulunca iki farklı cevap verdi.

```ruby
# paralel_atama.rb — a, b = b, a bir atamadir
a = 1
b = 2
a, b = b, a
puts a
puts b
puts defined?(a = 3)
```

```
2
1
assignment
```

Paralel atama `a, b = b, a` iki adın değerlerini değiş tokuş etti: `a` artık `2`, `b` ise `1`. Geçici üçüncü bir değişken gerekmedi, çünkü sağ taraf, sol taraftaki adlar yeniden bağlanmadan önce değerlendirildi. `defined?(a = 3)` ifadesi `"assignment"` bildirdi ve bu, önceki bölümün bulgusuyla uyumludur: atama bir ileti değil, dilin yazımıdır. `defined?` burada tek bir atamaya soruldu, paralel atamanın kendisine sorulmadı; değiş tokuşun bir yöntem çağrısıyla yapıldığını gösteren bir iz de çıktıda yoktur. İki değişkenin yerini değiştirmek, Ruby'de tek satırlık bir işlemdir; bu, adların nesneleri gösteren etiketler olduğunu, değerin ise etiketin arkasındaki nesne olduğunu bir kez daha gösterir.

**DT8.** Sınıf değişkeni (`@@`) yalnız `defined?` ile yoklandı. Sınıf değişkeninin kalıtımda nasıl paylaşıldığı bu kursun konusu değildir ve ölçülmedi.

## Atama Zinciri ve Dağıtma

Atamanın dilin yazımı olduğu ölçüldü. Bu bölüm atamanın üç ek biçimini yoklar: zincirleme atama, artan hedefe dağıtma ve eksik sağ taraf. Her biri aynı soruyu sorar: adlar nesneyi mi gösterir, değeri mi kopyalar? Eksen sözdizimidir; yalnız bir satırda `<<` iletisinin sahibi de basılır, çünkü zincirleme atamadan sonra nesneyi değiştiren şey bir iletidir.

```ruby
# atama_zinciri.rb — zincirleme atama ve dagitma
x = y = [1]
puts x.equal?(y)
y << 2
puts x.inspect
puts x.method(:<<).owner
bas, *kalan = 10, 20, 30
puts bas
puts kalan.inspect
ilk, = [7, 8]
puts ilk
p1, p2 = 1
puts p2.inspect
puts defined?(Math)
puts defined?(puts)
puts defined?(String.new)
```

```
true
[1, 2]
Array
10
[20, 30]
7
nil
constant
method
method
```

`x = y = [1]` yazımı iki adı da aynı nesneye bağladı: `x.equal?(y)` `true` verdi. Bu yüzden `y << 2` ile dizi değişince `x` de `[1, 2]` gösterdi. Burada değişikliği yapan şey atama değil, `<<` iletisidir ve onun sahibi `Array` çıktı. Yani atama nesneyi kopyalamadı, yalnız ad bağladı; nesneyi değiştiren bir ileti geldiğinde ise aynı nesneye bağlı bütün adlar değişikliği gördü. Bu, önceki bölümlerde kurulan sezginin sınanmasıdır: ad bir etikettir, değer ise etiketin arkasındaki nesnedir. Etiketin başka bir etikete atanması nesneyi çoğaltmaz.

Dağıtma biçimleri de dilin yazımıdır. `bas, *kalan = 10, 20, 30` ilk değeri `bas`'a, kalanları bir diziye verdi: `bas` `10`, `kalan` `[20, 30]` oldu. `ilk, = [7, 8]` yazımındaki sondaki virgül, hedeflerin yalnız ilkini aldığını belirtti ve `ilk` `7` oldu. Sağ taraf eksik kaldığında hata verilmedi: `p1, p2 = 1` satırında `p2` `nil` oldu. Son üç satır `defined?` sondasının farklı ifade türlerine verdiği cevaptır: `Math` için `constant`, `puts` için ve `String.new` için `method` çıktı. Sabitin `constant`, çağrının ise `method` olarak sınıflanması, `defined?` sondasının ifadenin neye benzediğine baktığını gösterir.

**DT9.** `defined?(Math)` sonucunun `constant` olması bu sürümde ölçüldü. Aynı sabit için başka sürümlerde farklı bir sözcük dönebilir; derste yazılan sözcük dilin sözü değil bu sürümün çıktısıdır.

## Tanım Sorgusu ve Üst Düzey Nesne

`defined?` yalnız yerel değişkenlere değil, her ad türüne bakar. Bu bölüm sondayı genel değişken, örnek değişkeni ve birkaç ifade üzerinde dener ve üst düzeydeki `self` nesnesinin ne olduğunu sorar. Eksen sözdizimidir: `defined?` bir yöntem değil dilin kendi işleci olduğu için sonuç, ifadenin neye benzediğiyle ilgilidir.

```ruby
# tanim_sorgusu.rb — her ad turu icin defined? cevabi
d1 = defined?($genel)
puts d1.inspect
$genel = 1
puts defined?($genel)
d2 = defined?(@ornek)
puts d2.inspect
@ornek = 2
puts defined?(@ornek)
puts defined?(self)
puts defined?(nil)
puts defined?(String)
puts defined?(3 + 4)
puts self.class
puts self.inspect
```

```
nil
global-variable
nil
instance-variable
self
nil
constant
method
Object
main
```

Genel değişken `$genel` atanmadan önce `nil`, atandıktan sonra `"global-variable"` verdi. Örnek değişkeni `@ornek` de aynı sırayı izledi: önce `nil`, sonra `"instance-variable"`. Yani tanımlı olmak, adın değil atamanın bir sonucudur: ad ancak bir değer bağlandığında tanımlı sayılır. `defined?(self)` `"self"` verdi, `defined?(nil)` ise `"nil"`, `defined?(String)` ise `"constant"` oldu. `defined?(3 + 4)` `"method"` bildirdi: sondayı ilgilendiren, ifadenin en dıştaki işleminin bir ileti olmasıdır.

Son iki satır, bütün bu dosyanın içinde çalıştığı nesneyi sordu. `self.class` `Object`, `self.inspect` ise `main` verdi. Yani bir `.rb` dosyasında alıcısız yazılan her ifade, sınıfı `Object` olan ve adı `main` basılan bir nesnenin içinde çalışır. Üst düzeyde atanan `@ornek` değişkeni de bu nesneye bağlıdır. Alıcısız yazılan bir çağrının, örneğin önceki bölümde `defined?` ile yoklanan `puts`'un örtük alıcısı da bu `main` nesnesidir. Sözdizimi kapsamı, adların nerede sorulduğunu belirler; `self` ise sorunun hangi nesnede yanıtlandığını. Bu bölümün sondaları aynı noktaya varır: `defined?` adın tanımlı olup olmadığını ve türünü söyler, ama değerini söylemez. Tanımlı olmayan ad `nil` verir, tanımlı olan ad kendi türünü bildirir. Bu iki cevap, bir adı kullanmadan önce yoklamak için yeterlidir. `3 + 4` için `method` cevabı gelse de cevabı veren yine `defined?` işlecidir: ifade çalıştırılmadı, yalnız biçimine bakıldı.

## Sınırlayıcı Ölçüm

Bu dersin yanıtlayanı sözdizimidir: `=` işaretinin ad bağlama davranışı dilin kendi yazımından gelir, bir sınıfın tanımladığı yöntemden gelmez. Burada kayma `+=` ile olur. `y += 1` yazıldığında içinde bir toplama olduğu için bunun bir ileti olduğu düşünülebilir. Ölçüm şunu soruyor: `y += 1`, `y ||= 3` ve `y + 1` aynı kategoride mi?

```ruby
# birlesik_atama.rb — += atamadir, icindeki toplama ise iletidir
y = 1

puts defined?(y += 1)
puts defined?(y ||= 3)
puts defined?(y + 1)
puts y
puts y.method(:+).owner
```

```
assignment
assignment
method
1
Integer
```

`defined?(y += 1)` ve `defined?(y ||= 3)` ikisi de `"assignment"` verdi, `y + 1` ise `"method"`. Ardından `puts y` hâlâ `1` bastı: `defined?` atamayı çalıştırmadı. Toplamanın yanıtlayanı ise önceki derste olduğu gibi `Integer`'dır. Aynı satırda iki iş görülür: adı bağlamak dilin işidir, yani sözdizimi; iki sayıyı toplamak sınıfın işidir. Bu dersin yanıtlayanı olarak yalnız birincisi sayılır, çünkü ders ad bağlama üzerine kuruludur.

Üç ölçümün ortak sonucu şudur: Ruby'de bir ad yazıldığında önce adın işaretine bakılır, sonra işaretin bildirdiği yere. Aynı `x = 5` ifadesi, başına `@` ya da `$` konunca başka bir yere yazılır, ama üçünde de `=` işaretini çalıştıran şey dilin kendisidir. Bu yüzden sonraki derslerde atamayı ayrıca ölçmeye gerek kalmayacak; bir ifadede `=` gördüğümüzde ileti aramayız.

## Özet

- Adın başındaki işaret, adın türünü belirler: işaretsiz küçük harf yerel değişken, `@` örnek değişkeni, `$` genel değişken, büyük harf sabittir.
- `defined?` ifadeyi çalıştırmadan türünü bildirir: tanımsız sabit için `nil`, atama için `"assignment"` döner.
- Sabit adın bağlanmasını işaretler ama nesneyi dondurmaz; sabite bağlı bir dizi değişebilir.
- Atama bir yöntem çağrısı değildir: `defined?` `a = 1` için `"assignment"`, `1 + 2` için `"method"` verir.
- Bu dersin yanıtlayanı sözdizimidir: `y += 1` ve `y ||= 3` atamadır, içindeki toplamayı ise `Integer` yanıtlar.
- `defined?` kapsamı da ölçer: yöntem gövdesi dıştaki yereli görmez (`nil`), blok görür (`"local-variable"`); `a, b = b, a` yerleri değiştirir, `x = y = [1]` iki adı aynı nesneye bağlar.

## Sonraki Adım

Ad bağlama dilin işi olarak ölçüldü. Dilin kendi yazımıyla çalışan başka yapılar da var: `if`, `while` ve `case`. Bunlardan `case`'in dallarını kim seçiyor, bir `when` satırı nesneye bir ileti mi gönderiyor? Sonraki ders, Denetim Akışı, bu soruyu ölçer.
