Junior
Go'da dilimler nasıl çalışır?
sobes.tech yapay zeka
AI'dan gelen yanıt
Bir dilim (slice), bir dizinin hafif bir kabuğudur. Kendisi veriyi depolamaz, bunun yerine temel dizine referans tutar.
Dilimin yapısı:
- Temel diziye işaretçi: Hafızadaki dilimin ilk öğesinin adresi.
- Uzunluk (Length): Dizideki öğe sayısı.
- Kapasite (Capacity): Temel dizideki toplam öğe sayısı, dilimin işaretçisinden itibaren erişilebilir olan.
// Bir dilim tanımlama örneği
var s []int
s = append(s, 1, 2, 3) // Öğeler ekleniyor
// Dilim s'nin iç yapısı (basitleştirilmiş)
// struct SliceHeader {
// Data uintptr // Temel diziye işaretçi
// Len int // Uzunluk
// Cap int // Kapasite
// }
make([]T, length, capacity)kullanılarak oluşturulan dilim, belirtilen kapasitede temel dizi oluşturur ve ona referans veren dilim, belirtilen uzunlukta.- Bir dizide veya başka bir dilimde dilim kullanılırken (örneğin,
arr[low:high:max]), yeni bir dilim oluşturulur ve aynı hafıza alanına referans verir, ancak farklı işaretçiler, uzunluk ve kapasiteye sahiptir. appendişlemi hafıza yeniden tahsisini tetikleyebilir. Eğer mevcut kapasite yeni öğeleri eklemeye yeterli değilse, Go daha büyük yeni bir temel dizi oluşturur, eski öğeleri kopyalar ve dilimin işaretçisini yeni diziye günceller. Bu, yeniden tahsis (reallocation) olarak adlandırılır. Append sırasında kapasite büyümesi üssel (çiftlenir) şekilde gerçekleşir.- Dilimler değer olarak geçirilir, ancak temel diziye işaretçi içerdiği için, dilim üzerindeki öğe değişiklikleri (indeks aracılığıyla) tüm dilimlerde görülebilir.
- Dilimin uzunluğunu dilimleme ile değiştirmek, temel diziyi etkilemez, ancak temel dizinin bir kısmına erişimi sınırlandırabilir.
Tablo: Uzunluk ve Kapasite Karşılaştırması
| Özellik | Uzunluk (Length) | Kapasite (Capacity) |
|---|---|---|
| Tanım | Dilimdeki gerçek öğe sayısı | Kapasite, yeniden tahsis olmadan dilimin tutabileceği maksimum öğe sayısı |
| Erişim | s[i] ile öğelere erişimde kullanılır |
append ile eklenebilecek öğe sayısını belirler, yeniden tahsis öncesi |
| Elde etme | len(s) |
cap(s) |
// Kapasite ve uzunluk ile çalışma örneği
s := make([]int, 0, 5) // Uzunluk 0, kapasite 5
fmt.Println(len(s), cap(s)) // 0 5
s = append(s, 1, 2) // 2 öğe ekleniyor
fmt.Println(len(s), cap(s)) // 2 5
s = append(s, 3, 4, 5, 6) // 4 öğe daha ekleniyor, yeniden tahsis gerek
fmt.Println(len(s), cap(s)) // 6 10 (kapasite arttı)