Johs Susser gerçekten çok geyik bir programcı. Aynı zamanda iyi de bir girişimcidir. Geçenlerde gönderdiği tweet ile uzun zamandır üzerinde düşündüğüm bir konuya değindi kendisi.

Eğer sizde şimdiye kadar en az bir defa değişik zaman dilimlerinde çalışan bir yazılım projesinde görev aldıysanız, muhtemelen siz de Josh’un bu fikrine katılıyorsunuzdur. Projenizdeki dosyaların server’lara yüklenme zamanlarını ve bunları farklı zaman diliminde yaşayan insanlara göstermekte zorluklar yaşayabilirsiniz. Özellikle .NET programcıları için DateTime sınıfının bazı sorunları olduğundan bu durum daha karmaşık hale gelebilir. Şöyle belirginleştirelim bu durumu. Aşağıdaki kod parçasını ele alalım;

 Console.WriteLine(DateTime.Now == DateTime.UtcNow); 

Aslına bakarsanız başlarda bu kodun ne yapması gerektiğini bir türlü kavrayamamıştım. Fakat biraz daha üzerinde kafa yormaya başlayınca önümde 3 seçenek belirmeye başladı;

  • Her zaman True yazdırır, ikisi de aynı zamanı gösterir, sadece biri local zamanı diğeri de evrensel zamanı.
  • Her zaman False yazdırır, bu iki değer farklı çeşit veriyi ifade eder, bu yüzden bunlar otomatik olarak eşit olamazlar.
  • Eğer yerel zamanınız UTC ile senkronize ise, zaman dilimine uyulmaksızın True döndürür ki bu iki değer eşittir.

Bu kod benim derlediğim 4 farklı yerdeki derleyicide de False sonucunu döndürdü. Kendi bilgisayarımdaki derleyicide False sonucunu döndürmesi çok doğal tabi ki, zira İstanbul UTC+02.00 zaman diliminde olduğundan bu iki değer hiçbir zaman aynı zamanı göstermezler. Herneyse, DateTime hakkında bu kadar dedikodu yeter. Şimdi asıl konumuza dönelim.

Tayland..

Bildiğiniz gibi dünya üzerinde kullanılan birden fazla takvim var. Bu takvimlerden birçoğu etkili bir insanın doğum günü ile başlar. Standart uluslararası takvim Hz. İsa’nın doğum yılını 1 olarak kabul eder, ondan önceki her yıl milattan önce kabul edilir. Budist takvimi Buddha’nın ölümü ile başlar.

Fakat Tayland takviminde göre Buddha’nın 2556 yıl önce vefat ettiğini, yani Hz. İsa’dan 543 sene önce vefat ettiğini belirtir. Bu yüzden eğer Miladi takvim ile Tayland’ta hangi yıl olduğuna bakmak isterseniz miladı yıla 543 yıl eklemeniz gerekir.

 2013 + 543 = 2556 

Peki kod ile bu yıla ulaşmaya çalışsak? Çok basit. Yeni bir ThaiBuddhistCalendar() nesnesi oluşturup bunun GetYear() methodunu şu anki local zaman parametresi ile çalıştırabilirz ;


Console.WriteLine(new ThaiBuddhistCalendar().GetYear(DateTime.Now)); // 2556

Peki bunu bir de DateTime nesnesi oluşturup ulaşmaya çalışsak?


DateTime d = new DateTime(2013, 1, 1, new ThaiBuddhistCalendar());
Console.WriteLine(d.Year); // 1470

Görüldüğü üzere, burada Budist takvimine göre bir DateTime nesnesini oluşturmamıza rağmen, Year özelliği 1470 değerini gösterir. Çünkü DateTime nesnesi, hangi takvimi kullanacağını yorumlayamaz. Varsayılan olarak her zaman Miladi Takvimi kullanır. Bu yüzden Budist takvimine göre 2013 yılı için oluşturduğumuz DateTime nesnesinin Year özelliği Budist takviminde 2013 yılının Miladi takvimde 1470 yılını gösterdiği için bu değeri alır.

Eğer günlük zaman kaydetme işlemlerinde ya da zaman dilimleri hakkında en iyi çözümleri öğrenmek isterseniz aşağıdaki konuya bir göz atmanızı tavsiye ederim;

Peki neden Tayland?

Aslında ThaiBuddhistCalendar()’ı kullanan en temel ülke olmasının yanı sıra asıl neden başka..

The Hangover Part II

Peki ya başlık?

Başlığın ilham kaynağı da Türk sinema tarihinin gülen adamı Kemal Sunal’dan gelsin..

  • http://ahmetalpbalkan.com/ ahmet alp balkan

    Selam Soner, 4 farkli derleyicide kodu derlemene gerek yoktu. :))

    Zira 2 expression (DateTime.Now ve DateTime.UtcNow) ayni anda evaluate edilmiyor. Yani a() == b() yaparken once a() yi calistiriyor bilgisayarin, “”sonra”” b()’yi calistiriyor.

    Farkli zamanlarda calisan iki sey sence ayni zamani dondurur mu? Ayni olmayan seyler esit olur mu? :)

    Datetime.Equals’in dokumantasyonuna gonderiyorum detayli bilgi icin http://msdn.microsoft.com/en-us/library/wk5t802s.aspx

    • http://sonergonul.net Soner Gönül

      Selamlar Ahmet,

      Teşekkürler yorumların için. Evet aslında bahsettiğin durum ikinci maddeye tekabul ediyor :) == ve DateTime.Equals aynı işlevi görüyor bir de. İkisi de InternalTicks property’sine göre bu iki değeri karşılaştırıyorlar..

      public static bool operator ==(DateTime d1, DateTime d2)
      {
      return d1.InternalTicks == d2.InternalTicks;
      }

  • http://ahmetalpbalkan.com/ ahmet alp balkan

    Bir ekleme daha yapayim. Evrensel olarak ayni zamana isaret eden iki Datetime, biri local biri UTC olsa bile esittir aslinda. Ustte yolladigim linkin remarks kismindan bunu okuyabilirsin.

    Yine de senin == ‘inin calismamasinin nedeni yukaridaki yorumda.

    • http://sonergonul.net Soner Gönül

      Hiç farkına varmamıştım ben o satırın çok saol.

      > Their Kind property values are not considered in the test for equality.

      Ayrıca bu DateTimeKind.Unspecified ne kadar hileli bir enumeration :)

  • Pingback: Takvim ve Yazılım | İREM ATICI