1 puan yazan GN⁺ 2023-08-09 | 1 yorum | WhatsApp'ta paylaş
  • Raku, Python, J, Frink ve Excel'in matematiksel iş akışlarındaki boşlukları doldurabilecek bir hesap makinesi dili adayı olarak değerlendirildi; kısa denemeler bile onun çok güçlü ama tuhaf bir dil olduğu izlenimini verdi
  • Unicode sembolleri, alfasayısal infix operatörler, liste çarpımı·zip·reduce·birikimli toplama, ~~ eşleştiricisi ve ... dizileri gibi özelliklerle operatör merkezli ifade gücü oldukça geniş
  • Kullanıcılar yalnızca infix operatörleri değil, circumfix/postcircumfix operatörleri de tanımlayabiliyor; ayrıca birleşme kuralları soldan/sağdan birleşmenin ötesinde zincir ve liste birleşmesini de kapsıyor
  • Çoklu dağıtım, yalnızca tür imzalarına göre değil where çalışma zamanı koşullarıyla da dallanıyor; fonksiyon imzaları ve içlerindeki parametreler de birinci sınıf değerler olarak ele alınabiliyor
  • Büyük kod tabanlarının bakımında yükü ağır görünüyor; ancak tek seferlik betikler, hesaplamalar ve kişisel araçlar gibi küçük ölçekli programlama için çekici; dokümantasyon, Windows REPL'i, derleme hızı ve sigil hataları başlıca engeller

Raku'ya bakma nedeni ve ilk izlenim

  • Raku, geçmişte Perl 6 olarak bilinen dil
  • Yazar, dinamik dillere dair şikâyetlerini yazdıktan sonra bazı kullanıcılar Raku'yu önerdi ve matematik işleri için bir hesap makinesi dili olmaya uygun olup olmadığını görmek üzere incelemeye başladı
  • Daha önce Python, J, Frink ve Excel'i birlikte kullanıyordu, ancak her birinin ciddi eksileri vardı
  • Birkaç gün denedikten sonra oluşan izlenim, “başka gremlinlerden bolca geri bildirim toplayarak bir dil tasarlamış gerçekten zeki gremlinler”e yakındı

Alışılmadık operatör sistemi

  • Raku, Unicode operatörlerini aktif biçimde kullanıyor
    • Bir kümenin eleman içerip içermediği ile kontrol ediliyor
    • , , de mevcut
  • Alfasayısal infix operatörlere de izin veriliyor
    • String tekrar operatörü x
    • Fonksiyon bileşimi o
  • Liste kombinasyonları da kısa sembollerle ifade ediliyor
    • X, listelerin Kartezyen çarpımını oluşturuyor
    • Xf, Kartezyen çarpımdaki her öğeye f uyguluyor
    • Zf ise aynı işi zip düzeninde yapıyor
  • Bir infix operatör f için [f] listeyi reduce eder, [\\f] ise birikimli sonucu üretir
    • [+] <1 2 3 4 5> sonucu 15
    • [\\+] <1 2 3 4 5> sonucu (1 3 6 10 15)

~~ eşleştiricisi ve ... dizileri

  • ~~, farklı karşılaştırma türlerini tek sözdiziminde ele alan bir eşleştirici olarak kullanılıyor
    • "abc" ~~ "abc" string eşleşmesini kontrol eder
    • "abc" ~~ Str, bunun string türünde olup olmadığını kontrol eder
    • "abc" ~~ {.chars == 3}, uzunluğun 3 olup olmadığını test eder
    • "abc" ~~ /^b/, abc ifadesinin b ile başlayıp başlamadığını kontrol eder
  • ..., önceki değerlerdeki örüntüyü yakalayıp bir dizi oluşturur
    • 0,1,2...10, 0'dan 10'a kadar 1'er artar
    • 0,2,4...10, çift sayılar dizisi olur
    • 1,2,4...10, 1 2 4 8 gibi artış örüntüsünü izler

Kullanıcı tanımlı operatörler

  • Raku, bazı dillerde olduğu gibi yalnızca infix operatör tanımlamakla kalmıyor; circumfix ve postcircumfix operatörler de oluşturulabiliyor
  • Örneğin sub circumfix:<[∀ zz>($inner){sum($inner)} gibi sarmalayan bir operatör tanımlanarak içteki değerler toplanabiliyor
  • Vektör iç çarpımı gibi görünen bir postcircumfix operatör de tanımlanabiliyor
    • sub postcircumfix:<| ⟩>(@left, @inside){[+] (@left Z* @inside)}
    • <1 2 3>|<4 5 6>⟩ sonucu 32
  • Operatör birleşme kuralları da çeşitli biçimlerde belirlenebiliyor
    • Olağan soldan birleşen ve sağdan birleşen infix operatörler tanımlanabiliyor
    • x < y < z ifadesinin x < y && y < z gibi yorumlandığı zincir birleşmesi belirtilebiliyor
    • a op b op c ifadesinin op(a, b, c) olduğu liste birleşmesi de destekleniyor

Çoklu dağıtım ve çalışma zamanı koşul dallanması

  • Raku, çoklu dağıtım destekliyor; farklı tür imzalarına sahip birden fazla fonksiyon tanımı arasından uygun olanı seçiyor
  • Örnek f fonksiyonu, argüman kombinasyonuna göre farklı davranıyor
    • Skaler ve dizi alırsa skaler değeri dizinin her öğesine ekliyor
    • Dizi ve skaler alan sürüm de destekleniyor
    • İki dizi alırsa her öğeyi Z+ ile topluyor
  • Daha ilginç olan nokta, değerlerin çalışma zamanı koşul belirteçleri ile de dağıtılabilmesi
    • multi my_abs(Int $x where {$x > 0}) {$x}
    • multi my_abs(Int $x) {-$x}
  • Bir fonksiyonun imzası birinci sınıf bir değer ve imzanın içindeki parametreler de öyle

Küçük özelliklerin yarattığı geniş yüzey alanı

  • MAIN fonksiyonu tanımlanırsa parametreleri otomatik olarak CLI bayraklarına dönüşüyor
  • Nesnelerde önceden sağlanan yöntem sayısı çok fazla
    • List object, tüm permütasyonları, tüm k-kombinasyonlarını ve tüm kayan pencereleri alma yöntemleri sunuyor
  • Junctions, aynı anda birden çok karşılaştırma yapmak için kullanılan sıra dışı bir değer biçimi
    • 1|2, any(1, 2) biçimine genişler ve 1 < 1|2 doğru olur
    • 1&2, all(1, 2) biçimine genişler ve 1 !< 1&2 doğru olur
  • Herhangi bir infix operatörün başına ! getirilerek olumsuzlama operatörü yapılabiliyor
  • Raku, hem $kebab-case isimleri hem de infix çıkarma işlemini aynı anda barındıran bir dil gibi görünüyor; bunu ayıran şeyin sigil sistemi olduğu tahmin ediliyor
  • regex syntax, Perl 5 ile geriye dönük uyumlu değil
    • Diller 30 yıl boyunca PCRE “standart”ını izlemiş olsa da Perl 6 bunu terk etmiş

Henüz bakılmayan alanlar ve küçük ölçekteki cazibesi

  • İncelenenler, hesap makinesi kullanımı odağındaki özelliklerin yalnızca bir kısmı
  • Nesne sistemi, paketler ve grammars henüz öğrenilmemiş
  • Fonksiyon gövdesindeki samewith'in aynı fonksiyonu yeni argümanlarla yeniden çağırması gibi, ele alınmayan pek çok özellik daha var
  • Bir Raku legacy kod tabanının bakımını yapmak gerekse bunun çok zor olacağı düşünülüyor; ama In The Small programlama için güçlü görünüyor
    • Tek seferlik betikler
    • Hesaplamalar
    • Kişisel araçlar
    • Başta istenen türden işler

Şikâyetler ve beklentiler

  • Dokümantasyon çok yetersiz ve sembollere bağımlılık nedeniyle arama yapmak zor
    • Dokümantasyonu zayıf başka dilleri öğrenmiş olmak bile burada yeterli olmayabilir; Raku çok daha büyük ve karmaşık olduğu için motivasyonu düşürebilir
  • Windows'ta REPL'e Unicode girildiğinde çökme yaşanıyor
  • Derleyici de oldukça yavaş; küçük dosyalar bile 0.5 saniyeden uzun sürüyor ve tekrar eden işler can sıkıcı hale geliyor
  • Sigil sistemi rahatsız edici
    • $x yerine @x yazılması gereken bir durumda hata ayıklamak için 30 dakika harcandığı bir örnek var
  • Genel olarak Raku beğeniliyor ve başarılı olması isteniyor; ancak zamanla özellikle derleme süresi ve dokümantasyonun iyileşmesi umuluyor

1 yorum

 
GN⁺ 2023-08-09
Hacker News yorumları
  • Programlama dillerini iki boyutlu bir alana yerleştirsek eksenler ne kadar şaşırttığı ve şaşırttığında bunun keyifli mi/korkunç mu olduğu olabilir.
    Normal dillerin genelde “pek şaşırtmayan ama ara sıra şaşırttığında da keyif veren” sol alt köşede olması sessizce beklenir; Raku ise nadiren dolu olan sol üst köşeyi açıkça hedefliyor gibi. Tavrı daha çok “Tuhaf, değil mi? Harika değil mi?” şeklinde.

    • Sorun şu ki bu eksenler öznel. Bir şey hem keyifli hem de korkunç olabilir; eskiden document.write = function ... gibi JavaScript yazmıştım ve gereken işi yaptığı için keyifliydi ama aynı zamanda epey korkunçtu.
    • Üniversite ödevi için bir parser yazmam gerektiğinde Raku’nun grammar özelliğini öğrendim; neredeyse her şeyi benim yerime yaptığı için hile kodu gibi hissettirdi ama yine de eğlenceliydi.
    • Sonuçta aslen Perl 6 idi; Perl geliştiricilerinin başka dillere hiç benzemeyen bir dil istemiş olması şaşırtıcı değil.
      Perl’de de çok sayıda “keyifli sürpriz” vardı; bence Raku esas olarak Perl’ün korkunç sürprizlerini ortadan kaldırmaya yönelik tasarlanmıştı.
    • ile küme üyeliğini kontrol etme kısmında ne demek istendiğini anlıyorum.
      0,2,4...10 (0 2 4 6 8 10) oluyor ama 1,2,4...10’un (1 2 4 8) olması “OEIS’te bir sonraki sayıyı mı arıyor?” dedirtiyor.
    • Raku, paragraf ilerledikçe giderek sağ üst bölgeye, yani şaşırtıcı ve korkunç alana gidiyor gibi görünüyordu.
  • Raku bir dil olarak ilginç, ama bazı idiomlar kafama pek oturmuyor.
    AppleScript’in doğal dil gibi görünmeye çalışırken tuhaf hissettirmesine benzer biçimde; my, say, sub, gather gibi doğal dilimsi öğeler, @ gibi semboller, modül bildirimleri ve dışarıdan bakınca Bizans işi görünen sözdizimi kararları bir arada. 99 bottles örneği mantıksal olarak takip edilebiliyor ama sezgisel olarak keşfetmesi zor. Çok fazla sembol var ve bağlama göre aşırı yüklenmiş gibi hissettiriyor; doğal dil parser’ı gibi Raku’nun ideal olabileceği işlerde bile bizzat kullanmak istemem.
    https://examples.raku.org/categories/module-management/Fletc...

    • Perl kullanmamış gibisin. Perl geçmişin varsa bu sözdiziminin önemli bir kısmı, özellikle dizileri ifade eden @ sigil’i oldukça tanıdık görünür.
    • Bash’e bakınca da aynı şeyi hissediyorum.
  • Raku’da en sevdiğim özellik, tamsayı bölmesinin ve ondalık literallerin ikisinin de rasyonel sayı tipi olan Rat döndürmesi.
    Herkes kayan noktanın pek iyi olmadığını bilir ama ondan gerçekten uzaklaşmaya çalışan dil sayısı çok az; Raku’da kayan nokta literali olması için bilimsel gösterim kullanmanız gerekir.

    • Common Lisp ve Scheme gibi daha eski diller de IEEE 754 kayan noktadan hoşlanmayanların kendilerini fark etmesini bekliyor.
      Bunların rasyonel sayıları ve karmaşık rasyonel sayıları da içeren bir sayı hiyerarşisi var; keyfi duyarlıklı sayıları da doğal olarak destekliyorlar. Birleştirilebilirlik harika.
    • Bu aslında kötü bir özelliğe daha yakın. Çünkü Rat temsili çok büyürse otomatik olarak kayan noktaya dönüşüyor.
      1/10 bir Rat, ama 1/100000000000000000000 bir Num oluyor. Yükseltilmeyen FatRat da var ama varsayılan değil.
    • Scheme’in sayı hiyerarşisi tam temsili onlarca yıldır düzgün şekilde ele alıyor.
      Bu yüzden bunu “belirsiz kayan noktayı açıkça istememişken bile kullanma biçiminden uzaklaştı” diye değil, en başta hiç öyle bir durumda olmamıştı diye görmek daha doğru.
    • Racket da farklı konuşur. Düzgün çalışıyor.
      (/ 1.0 3.0) 0.3333333333333333, (/ 1 3) 1/3, (- (+ 0.1 0.2) 0.3) ise 5.551115123125783e-17 olur.
    • Bunun iyi olduğundan emin değilim. Ondalık/rasyonel tipleri ve kayan noktayı ne zaman kullanmak gerektiğini biliyorum, ama kişisel Python kodlarımda Decimal() çağrısından çok daha fazla float() çağrısı var.
      Parayla doğrudan uğraşmadığım sürece neredeyse her zaman kayan nokta istediğim tercihtir.
  • Raku belgelerinin “gerçekten berbat” olduğunu düşünmedim; aksine resmi belge sitesi hem kavramsal belgeleri hem de API belgelerini içeren tek durak kaynak olarak etkileyiciydi.
    https://docs.raku.org/
    Kavramsal belgeler için başlangıç noktası olarak bu sayfa çok iyi: https://docs.raku.org/language

    • Birkaç yıldır Raku kullanıyorum; belgeler hem harika hem de yetersiz.
      Var olan içeriğin çoğu iyi yazılmış ve yararlı örnek kodlar içeriyor, ama bazen hiç belgelenmemiş ya da yalnızca basit durumları ele alan kısımlarla karşılaşıyorum. Özellikle modül sistemi en sorunlu olanıydı; modül/paket ayrımını yalnızca Modules sayfasını okuyarak anlamak zor. İçe aktarılan ad alanı ile bildirilen ad alanı farklı olabiliyor, ama derleyicinin bulabilmesi için dizin yapısının ad alanıyla eşleşmesi gerekiyor; bu yararlı ve tuhaf biçimde mantıklı, ama deneyerek öğrenmek zorunda kaldım.
    • Bu Perl kültüründen kaynaklanıyor. Perl FAQ ve kılavuz sayfaları, Perl kullanan programcıların mizacı sayesinde üst düzeydeydi; nükteli, özlü ve tuhaftılar.
    • Perl kılavuz sayfaları her zaman harikaydı.
  • Raku’nun havalı Unicode operatörlerinin hepsinin ASCII alternatif gösterimi var.
    Örneğin , , , için alternatif gösterimler (elem), !(elem), (cont), !(cont) şeklinde.
    https://docs.raku.org/language/unicode_ascii#Other_acceptabl...

    • Ben kesinlikle ASCII sürümleri kullanırdım.
  • Dili iyi tanımadan ortaya çıkan tipik eleştirilerin hâlâ tekrarlandığı görülüyor. Eskiden Perl için “line noise” denirdi, şimdi de Raku’nun Unicode operatörlerini çekinmeden kullandığı söyleniyor
    Ama bunlar isteğe bağlı; kodun ekranda küçük ve ifade gücü yüksek görünmesi için bizzat denedim. Dikkatli ve yaratıcı Unicode kullanımı için gayet uygun. Sigil’lerden hoşlanmama tepkisi de yaygın, ama Perl’in İsviçre çakısı motorlu testere gibi ifade gücünü sevdiğim için Raku/Perl 6 kullanıyordum; Raku, Perl’i Perl yapan şeylerin karesini almış gibi. Daha düzenli, ifade gücü yüksek ve eski güzel Perl’in üzerine devasa bir özellik yığını eklenmiş. Belgeleri de iyi, ama sürekli elden geçirilmesi gerekiyor; Perl belgeleriyle karşılaştırınca çıta çok yüksek

    • ASCII dışı operatörlerin nasıl girildiğini merak ediyorum. Özel bir klavye düzeni mi, editörün belirli dizileri otomatik dönüştürmesi mi, yoksa ham Unicode escape’leri mi kullanılıyor bilmiyorum
      Birkaç karakter tasarruf etmek için bunu yapmak karmaşık ve pek anlamlı görünmüyor
  • Sözdizim şekeriyle dolu bir programlama dilinin nasıl görüneceğini bazen merak ederdim; artık biliyorum
    “Berbat ama tuhaf biçimde çekici, gözümü alamıyorum, daha fazlasını göster” gibi bir his

    • Son birkaç Advent of Code’u kazanan kişinin yaptığı hobi dili noulith hoşuna gidebilir
      GitHub açıklamasında “slaps roof of [programming language]* this bad boy can fit so much [syntax sugar] into it.” yazıyor. En son Advent of Code’u da o dili kullanarak kazandı: https://github.com/betaveros/noulith
    • Raku’nun Grammars özelliğini öğrenene kadar bekle
    • Modern C++’ı her gördüğümde aynı tepkiyi veriyorum
  • Raku’nun aslında Perl 6 olarak başladığını ve tasarım felsefesinin büyük bölümünün Perl tarzı düşünceden çıktığını hatırlamakta fayda var
    Yazarın string tekrarı için kullanılan x operatörüne hemen tepki vermesine bakılırsa Perl ve Raku tarihini pek bilmiyor gibi görünüyor; oysa bu Perl’de onlarca yıldır böyleydi

    • Metinde “regex sözdizimi Perl 5 ile geriye dönük uyumlu değildir. 30 yıl boyunca diller PCRE ‘standardını’ izledi, Perl 6 ise hepsini olduğu gibi attı” cümlesi var; yani en azından bir ölçüde biliyor gibi
    • İlk dipnotta Raku’nun eskiden Perl 6 olarak bilindiği yazıyor
    • “Perl6/Raku, Perl 5’ten tamamen farklıdır” abartısı fazla şişirilmiş
      Boşuna Perl 6 denmedi; neredeyse aynı Perl ekibi geliştirdi. Perl 5’i epey kullanmış biri için Perl6/Raku’nun mirası açıkça görülür. Raku’nun nesne modelinin tamamı da CPAN’deki Perl 5 modülü Moose.pm’in biraz daha güçlü bir sürümüne yakın
  • Dürüst olmak gerekirse Perl 5/PCRE regex sözdizimi berbat
    Var olmasının nedeni de eski regex sözdiziminde (? ifadesinin sözdizimi hatası olması ve bu yüzden herhangi bir anlam için yeniden tanımlanabilmesinden ibaret. Raku, regex’in neyi ifade etmesi gerektiğini artık bildiğimiz bir zamanda, baştan aklı başında bir regex dili tasarlama girişimi. Alternatif, önümüzdeki 30 yıl daha (?:this|(?>or that)) gibi şeylere hapsolmak

    • Berbat olmaktan çok çözülemez bir kara büyü; anladıktan sonra ise havalı
      Perl’e dokunmayalı uzun zaman oldu ama regex’i hâlâ sık kullanıyorum
    • Katılıyorum, ama gerçekten çok kullanışlı
  • Belirli bir anlamda kesinlikle gremlin. Tuhaf ve karmaşık ama üretkenliği artıran araçları seviyorum
    Yine de “büyük programlar vs küçük programlar” karşılaştırmasına katılmıyorum. Daha az bilge biri bunu büyük işler için kötü bir dil olduğu anlamına yorabilir, ama gerçekte diğer diller kadar iyi, hatta daha iyi bile olabilir. Sorun, diğer gremlin dillerinde olduğu gibi, iyi kullanmak için bilgelik gerekmesi. Örneğin $x ile @x’i karıştıran biri, benzer dilleri yeterince kullanmışsa neredeyse hiç çıkmaz. Sigil’ler kodu okurken değişkenin basit tipini, Raku’da ise arayüzünü hemen gösterdiği için işleri aslında kolaylaştırır; aynı değişken ad alanını farklı sigil’lerle yararlı biçimde kullanabilirsiniz. Garip görünür, gereksiz karakterler gibi durur ve anlamını bilmek gerekir, ama hayatı kolaylaştırabilir: https://www.perl.com/article/on-sigils/
    Sorun, ne yaptığını pek bilmeyen kişilerde ortaya çıkar. Böyle insanlar için bu gremlin dili yaşayan bir kâbus olabilir; bowling bariyerleri, kolluklar, Kevlar eldivenler, baret, GPS gibi çok sayıda korumaya ihtiyaç duyarlar. Bu, gremlin diliyle gökdelen inşa edilemez demek değil; kazaya yatkın gremlin olmayanlar inşa edemez, bilge gremlinler ise edebilir

    • “Bu aracı yalnızca yeterince iyi olanlar kullanabilir” zihniyetini devasa bir tasarım kokusu olarak görüyorum
      Araçlar, ekibin ihtiyaç duyduğu işi daha iyi ya da daha hızlı yapmasına yardımcı olmak için vardır. Junior’ları elemek ya da kendi egonu beslemek için gereksiz derecede karmaşık araçlar kullanıyorsan, o araç organizasyonun geri kalanı için yardımcı olmaktan çok silaha yakındır