May 23, 2022

Merhaba,

Ufkunuzu açacak bir olay var! D'de aralıklarla çalışırken, birazdan eşlemleme (map'leme) ile veri-> f()-> işlem arasına girip sayma ve/veya toplama yapacağız. Gerçi tespit edeceklerimiz bir sorun gibi duruyor ama hani derler ya: "her şerde bir hayır vardır" diye. Öyleyse buyrun bakalım ne cinlikler dönüyor...:)

Şimdi yeni geliştirilen önbellekleme yani cached() özelliğine tekrar giriş yapacağım. Aslında Ali Çehreli'nin (aynı zamanda olanağı geliştiren teacher, writer&programmer olan değerli dostumuzun), sorunu göstermek için ilk örneği şöyleydi:

import ali.cached;
import std.stdio;
import std.algorithm;
import std.range;

void main() {
  size_t hesapAdedi = 0;

  auto r = iota(10)
           .map!((i) {
               // writeln(i, " için hesaplanıyor");
               ++hesapAdedi;
               return i;
             })
           .filter!(i => i % 2)
           .slide!(No.withPartial)(2);

  writefln("%-(%s%)", r);

  writeln("Hesap adedi: ", hesapAdedi);
} /* ÇIKTISI:
[1, 3][3, 5][5, 7][7, 9]
Hesap adedi: 46
*/

Kaynak: https://forum.dlang.org/thread/t2da1u$2qkr$1@digitalmars.com
(10 Nisan 2022 Buluşma Duyurusu'nın ilk iletisi)

Denemek için birer aralık ve işlevli benim örneğim ise aşağıdaki gibi:

struct Miniyota {
  int last, front;
  void popFront() { ++front; }
  bool empty() { return front > last; }
  auto save() { return this; }
}

int _x_;
int Sum(ref int x) { // sum and dispatch
  _x_ += x;
  return x;
}

void main() {
  auto r = Miniyota(6);
  auto s = r.map!(i => i.Sum)
            //.cached
            .filter!(i => i % 2)
            .slide!(No.withPartial)(2).join;

  r.writeln; // [0, 1, 2, 3, 4, 5, 6]
  s.writeln; // [0, 1, 3, 3, 5]
  "Sum by slider: ".writeln(_x_); /*
   =36 (12 steps without filter)
   =79 (28 steps for odd numbers)
}

Aralık, Miniyota (mini iota) isminde basit bir yapı tarafından ve 0'dan 6'ya kadar ardışık sayılardan oluşuyor. Biz bunları değişik şekillerde (sayma, toplama, çiftleri filitreleme, kaydırma vb.) işleyeceğiz. Sonuçları basit şekilde ekrana yazıyoruz ama birden fazla olasılık var. Lütfen satırları aç/kapa yaparak olasılıkları görmeye ve neden böyle sonuçlar aldığınızı anlamaya çalışın...

Normalde 7 eleman var ve bunların toplamları 21 olması gerekiyordu. Ama slider() yüzünden 36'ya (bu sayı ilginç şekilde n²'ye eşit) çıkıyor çünkü baş ile sondaki elemanlar hariç 2 kere erişiliyor ve bu esktradan 5(+7 = 12) adım demek. Eğer tek sayılar üzerinde işlem yapmak isterseniz bu sefer toplam erişim 28 adıma kadar yükseliyor ve istenmeyen 79 toplamı elde ediliyor!

Bu bir sorun çünkü sizin veri kaynağınız bellekte çalışmayan başka bi'şey olabilirdi, mesela HTTP/PUT metodu ile JSON array alıyor da olabilirdiniz. Belki de önbellekleme yapılmıyor ve 2. bir request olasılığınız yoktu ha!
(-bknz. ref.HTTP Methods ne dersiniz?)

Özetle örneklerde düzenleme yaparak ve yakında yayınlanacak olan önbellekleme olanağı ile karşılaştırarak kendi sonuçlarınıza erişebilirsiniz.

Dip Not: Aslında bu sorun, save() olanağı ile önceki pozisyon kaydedildiği için oluyor. Lütfen bunu da dikkate alın.

Başarılar...