C# 6.0 ile Gelen Yenilikler

Microsoft C# 6.0 'ı daha önce release ettiği sürümlere istinaden çok büyük major feature'lar ile kullanıma sunmadı desek çokta yanlış olmaz herhalde. Ancak 6.0 ile major feature'ların dışında geliştirici için development yapmasını çok daha kolaylaştıracak diyebileceğimiz bir takım önemli değişiklikler sundu. Daha öncesinde aynı işlemleri yapabilmek için satırlarca kod yazdığımız işlemler artık birkaç satırda yapılabilecek duruma gelmiş.  6.o ile gelen feature listesi aşağıda ki gibidir.   1) Auto-Property Initializer Daha önceki C# sürümlerinde field'lar için kullanılabilir olan initializer artık auto-property'ler için de kullanılabilecek.  Öncesinde using System; namespace CSharpSix { class Program { static void Main(string[] args) { Customer cust = new Customer(); Console.WriteLine(cust.customerID); Console.ReadLine(); } } public class Customer { public Customer() { customerID = Guid.NewGuid(); } public Guid customerID { get; set; } } }  C# 6.0 ile using System; using static System.Console; namespace CSharpSix { class Program { static void Main(string[] args) { Customer cust = new Customer(); WriteLine(cust.customerID); ReadLine(); } } public class Customer { public Guid customerID { get; set; } = Guid.NewGuid(); } }    2) Using Static Daha önceleri projede ilgili class'ta herhangi bir yerde static sınıfları kullanmak istediğimizde sınıfın adıyla birlikte o sınıfın fonksiyonlarını çağıra bilmekteydik.  Öncesinde class Program { static void Main() { Console.WriteLine(Math.Sqrt(5*2 + 4*3)); Console.WriteLine(System.DayOfWeek.Friday - System.DayOfWeek.Monday); } } Artık C# 6.0 ile birlikte bu statik sınıfları using ile tanımlayıp sonrasında o sınıfa ait metotları kullanabileceğiz.  C# 6.0 ile using static System.Console; using static System.Math; using static System.DayOfWeek; class Program { static void Main() { WriteLine(Sqrt(5*2 + 4*3)); WriteLine(Friday - Monday); } }   3) Expression-bodied methods Lambda expresiion C# 3.5 ile gelen en büyük değişiklikti ve lambda sayesinde uzuuunnn mu uzun delegate kodları yazmaktansa o satırlara karşılık gelen lambda tanımlamalarını yazabilmekteyiz. Eğer yazılan metod geriye tek satırlık bir işlem yapıp değeri return ediyorsa bu işlem lambda expression ile de yazılabilecektir.  Öncesinde namespace CSharpSix { class Program { private static double MultiplyNumbers(double num1, double num2) { return num1 * num2; } static void Main(string[] args) { double num1 = 3; double num2 = 6; Console.WriteLine(MultiplyNumbers(num1, num2)); Console.ReadLine(); } } } C# 6.0 ile using static System.Console; namespace CSharpSix { class Program { private static double MultiplyNumbers(double num1, double num2) => num1 * num2; static void Main(string[] args) { double num1 = 3; double num2 = 6; WriteLine(MultiplyNumbers(num1, num2)); ReadLine(); } } }   4) Null Conditional Operator Developerlar için kaçınılmazdır ki bir objenin veya tanımlanmış olan bir değerin "null" mı değil mi diye sürekli kontrol etme durumunda kalmışızdır ve bu kontrol için genelde min 2 satır kod yazmak zorundayızdır. if(obj!=null) ... şeklinde. C# 6.0 ile birlikte null check yapma işlemleri biraz daha kolay hale getirilmiş. Öncesinde using System; namespace CSharpSix { class Program { static void Main(string[] args) { Person person = new Person(); if (person.Name == String.Empty) { person = null; } Console.WriteLine(person != null ? person.Name : "Field is null."); Console.ReadLine(); } } public class Person { public string Name { get; set; } } } C# 6.0 ile using System; using static System.Console; namespace CSharpSix { class Program { static void Main(string[] args) { Person person = new Person(); if (person.Name == String.Empty) { person = null; } WriteLine(person?.Name ?? "Field is null."); ReadLine(); } } public class Person { public string Name { get; set; } = ""; } }   5) String Interpolation String bir ifadeyi formatlayıp farklı şekilde bir string birleştirme işlemi vs yaparak göstermek itediğimizde string.format("{0} {1}","Caner", "Tosuner"); vs şeklinde tanımlıyorduk. 6.0 il birlikte bu formatları ve ifadeleri yapmak biraz daha kısa hale getirilmiş diyebiliriz.  Öncesinde using System; namespace CSharpSix { class Program { static void Main(string[] args) { string firstName = "Caner"; string lastName = "Tosuner"; Console.WriteLine("Name : " + firstName + " " + lastName); Console.WriteLine("Name : {0} {1}", firstName, lastName); Console.ReadLine(); } } } C# 6.0 ile using static System.Console; namespace CSharpSix { class Program { static void Main(string[] args) { string firstName = "Caner"; string lastName = "Tosuner"; WriteLine($"{firstName} {lastName} is my name!"); ReadLine(); } } } Bu yazım şekliyle birlikte string format yazımının karmaşasından da kurtulmuş oluyoruz.   6) Exception Filters try içerisinde bir exception alınıp carch'e düştüğünde exceptiona neden olan şeyle ilgili bir spesification yapmak istediğimizde genelde catch bloğu içerisinde if(ex.Message.Equals("bişey bişey")) şeklidne yazarız. 6.0 ile catch bloğu yanına bu if condition'ları yazabilir hale geliyoruz ve her condition'nın kendi catch'i oluyor. Öncesinde  using System; namespace CSharpSix { class Program { static void Main(string[] args) { try { throw new Exception(404); } catch (Exception ex) { if (ex.Message.Equals("500")) Console.Write("Bad Request"); else if (ex.Message.Equals("401")) Console.Write("Unauthorized"); else if (ex.Message.Equals("402")) Console.Write("Payment Required"); else if (ex.Message.Equals("403")) Console.Write("Forbidden"); else if (ex.Message.Equals("404")) Console.Write("Not Found"); } Console.ReadLine(); } } } C# 6.0 ile using System; using static System.Console; namespace CSharpSix { class Program { static void Main(string[] args) { try { throw new Exception(404); } catch (Exception ex) if (ex.Message.Equals("400")) { Write("Bad Request"); } catch (Exception ex) if (ex.Message.Equals("401")) { Write("Unauthorized"); } catch (Exception ex) if (ex.Message.Equals("402")) { Write("Payment Required"); } catch (Exception ex) if (ex.Message.Equals("403")) { Write("Forbidden"); } catch (Exception ex) if (ex.Message.Equals("404")) { Write("Not Found"); } ReadLine(); } } }   7) Await in a Catch and Finally Block C# 6. ile birlikte artık Catch ve Finally blockları arasında await keyword'ünü kullanıp asynchronous çalışan kodlar yazabiliyoruz. Daha önce bunu yapabilmemiz mümkün değildi ve ihtiyaç halinde (logging etc.) çeşitli kontroller yapıp catch bloğundan çıktıktan sonra async yapmak istediğimiz işlemi yapardık. Öncesinde  using System; using System.Net.Http; using System.Threading.Tasks; namespace CSharpSix { class Program { static void Main(string[] args) { bool isException=false; try { throw new notimplementedexception(); } catch (Exception exception) { isException = true; } if(isException) var result = await LogManager.Log("Hata oluştu !" + exception.Message); Console.ReadLine(); } } } C# 6.0 ile using System; using System.Net.Http; using System.Threading.Tasks; using static System.Console; namespace CSharpSix { class Program { static void Main(string[] args) { try { throw new notimplementedexception(); } catch (Exception exception) { var result = await LogManager.Log("Catch => Hata oluştu !" + exception.Message); } finally { var result = await LogManager.Log("Finally => Hata oluştu !" + exception.Message); } ReadLine(); } } }   8) Index initializers Önceden bir List'e veya Dictionary'ye belirli bir index'ine item atamak istediğimizde önce initialize eder sonra nokta operatörüyle değerleri atardır. 6.0 ile birlikte initialize sırasında bu bu atam işlemlerini yapabilmekteyiz. Öncesinde  using System; namespace CSharpSix { class Program { static void Main(string[] args) { var dic = new Dictionary<int, string> { { 1, "one" }, { 4, "four" }, { 10, "ten" } }; } } } C# 6.0 ile using System; namespace CSharpSix { class Program { static void Main(string[] args) { var dic = new Dictionary<int, string> { [1] = "one", [4] = "four", [10] = "ten" }; } } } Yukarıda 2 syntax'a baktığımızda ne fark var ki ikisi de aynı diyebiliriz ancak şöyle bir ayrım var. 6.0'dan önceki yazımda .Add() metodu kullanılarak initialize işlemi yapılıyor. Yeni syntax'da ise direkt olarak index assignments kullanılmakta ve bu da performans olarak daha verimli bir hale gelmekte.    9) nameof Operatörü Tanımlamış olduğumuz değişkenin veya objenin string olarak adına ulaşmak istediğimizde 6.0 ile birlikte gelen nameof operatörünü kullanabiliriz. Öncesinde  using System; namespace CSharpSix { class Program { static void Main(string[] args) { DoSomething("Selam"); Console.ReadLine(); } public static void DoSomething(string name) { if (name == null) throw new Exception("Name is null"); } } } C# 6.0 ile using System; using static System.Console; namespace CSharpSix { class Program { static void Main(string[] args) { DoSomething("Selam"); ReadLine(); } public static void DoSomething(string newName) { if (newName == null) throw new Exception(nameof(newName) + " is null"); } } }

C# Ref ve Out Kullanımı

Object-Oriented programramming ile birlikte günümüz PC'lerinin de geçmişe göre bir hayli performanslı olması biz developer'ları git gide programlama dili & RAM ilişkisinden uzaklaştırıyor. Çok iyi hatırlıyorum üniversite 1. sınıfta C++ dersi almıştım ve dersi anlatan hoca ilk derste yanılmıyorsam şöyle bir cümle kurmuştu "Muhtemelen birçoğunuz ilk ve son defa bu derste Programlama ve RAM ilişkisini bu kadar yakından öğrenme şansınız olacak..". Tabi hoca bunu söylerken ne yazık ki bizde öyle çokta anlıyormuş gibi dinlememiştik. C# programlama dilinde kullanılan veri tiplerini 2 başlıkta tanımlayabiliriz. Değer tipleri ve Referans tipleri. Kısaca tanımlamak gerekirse, değer tipler; ram de kaplayacağı alanı belli olan int,double,byte vs gibi struct olan tiplerdir ve stack'de bulunurlar. Referans tipler; string,object, kendi yazdığımız custom objeler bunlar ram'de kaplayacakları alan belli olmadığından heap'de tutulurlar.  Gelelim konumuzun başlığında bulunan "ref" ve "out" parametrelerimize. C# da kullanıma sunulan ref ve out isminde iki tane parametre tanımlama çeşidi bulunmakta. Bu kullanımlarla birlikte ref ve out parametreleriyle yazmış olduğumuz metodlara değişkenleri göndermeden önceki değerleri ile metoddan çıktıktan sonraki değerleri kullanıma göre farklılıklar göstermektedir. Aslında ref veya out ile tanımlandığında RAM'de ne oluyor tanımlanmadığında ne oluyor, aralarında ne gibi farklar var bunları incelicez.   Geliştirme yaparken tanımlamış olduğumuz parametre alan metodları kullanmak istediğimizde ilgili metoda parametre geçme işlemi 2 yolla yapılır "pass by value" ve "pass by reference". Kısaca tanımlamak  gerekirse ; Pass by value fonksiyona parametre gönderirken o parametrenin bir kopyasının oluşturulup gönderilmesi ve metod içerisinde yapılan değişikliklerden metod içerisinde ki yeni değerin etkilenmesi, Pass by reference fonksiyona parametre gönderirken o parametrenin ram'de adresinin gönderilip metod içerisindeki yapılan değişiklerden orjinal değerin etkilenmesi.   Ref - Out Nedir den önce aşağıdaki örneği bir inceleyelim; C# da geriye herhangi bir değer dönmeyen bir metod yazalım ve içerisine int tipinde 3 değişken alsın sonrasında bu değerlerden birini metod içerisinde değiştirsin ve değişkenin metoddan önceki ve sonraki değerlerine bir bakalım  public class RefOutExample { static void Main() { int originalValue = 43; Console.WriteLine("ChangeMethod'dan önce: " + originalValue);//Output 43 ChangeMethod(1,3,originalValue); Console.WriteLine("ChangeMethod'dan sonra: " + originalValue); //Output 43 } static void ChangeMethod(int x, int y, int i) { i = i+x+y;//47 } }   Yukarıda ki örnekte ChangeMethod'isimli metoda parametreyi geçereken değişkenin orjinal halini değilde bir örneğini geçtiğimizden metod içerisinde ki değişiklik orjinal değeri etkilemedi.   C# Ref Kullanımı Value Type'lar metodlara birebir kopyası oluşturularak geçirilirler ve metod içerisinde o değişkenle ilgili yapılan değişikliklerden orjinal değer etkilenmez. Ancak bazen değer tiplerini de referansları ile metodlara parametre olarak vermek isteyebiliriz. Referans yolu ile metoda parametre olarak geçtiğimiz değişken üzerinde yapılacak bütün değişiklikler orjinal değeri etkileyecektir çünkü artık o metod içerisinde değişkenin bir kopyası değilde RAM'de ki adresi bulunmaktadır. Örnek kullanımı aşağıdaki gibidir. using System; public class RefOutExample { public static void Main() { int originalValue = 43; Console.WriteLine("ChangeMethod'dan önce: " + originalValue);//Output 43 ChangeMethod(1,3,ref originalValue); Console.WriteLine("ChangeMethod'dan sonra: " + originalValue); //Output 47 } static void ChangeMethod(int x,int y, ref int i) { i = i+x+y;//47 } }   Yukarıda görüldüğü gibi ChangeMethod'una bu sefer parametreyi ref keyword'ü kullanarak geçtik ve bu metoda o değişkenin örneğini değilde RAM'de bulunan adresini geçtiğinden "i" parametresi metodu çağırırken kullandığımız "originalValue" değerine refer ettiğinden yapılan bir değişiklik "originalValue" parametresinin kendisine yapılmıştır.   Ref'in Özellikleri Metodu tanımlarken referans yolu ile iletilmek istenen değişkenin önüne "ref" yazılmalıdır.  originalValue değişkeni metoda parametre olarak geçilmeden önce bir başlangıç değeri almak zorundadır, "i" değişkeni metod içerisinde herhangi bir değişiklik yapmadan da kullanılabilir.     C# Out Kullanımı Out aslında ref ile hemen hemen aynı amaca hizmet ediyor diyebiliriz. Ancak ref ile aralarında temel 2 farklılık var bunları aşağıda ki Ref-Out Farklılıkları başlığında yazıyor olacağım   Out'un Özellikleri Metodu tanımlarken geçilmek istenen değişkenin önüne "out" yazılmalıdır.  originalValue değişkeni metoda parametre olarak geçilmeden önce bir başlangıç değeri almak zorunda değildir. "i" değişkeni metod içerisinde herhangi bir değişiklik yapmadan kullanılamaz.   Yukarıda Ref için yazdığımız metodun aynısını Out içinde yazalım using System; public class RefOutExample { public static void Main() { int originalValue; ChangeMethod(1,3,ref originalValue); Console.WriteLine("ChangeMethod'dan sonra: " + originalValue); //Output 47 } static void ChangeMethod(int x,int y, out int i) { i = i+x+y;//47 } }   Ref-Out Farklılıkları Ref Out Metodu tanımlarken geçilmek istenen değişkenin önüne "ref" yazılmalıdır. Metodu tanımlarken geçilmek istenen değişkenin önüne "out" yazılmalıdır. originalValue değişkeni metoda parametre olarak geçilmeden önce bir başlangıç değeri almak zorundadır. originalValue değişkeni metoda parametre olarak geçilmeden önce bir başlangıç değeri almak zorunda değildir. "i" değişkeni metod içerisinde herhangi bir değişiklik yapmadan da kullanılabilir. "i" değişkeni metod içerisinde herhangi bir değişiklik yapmadan kullanılamaz.     Aynı metodda hem "ref" hem "out" kullanımı Gelin birde hem ref hem out tanımlı parametreleri olan bir metod kullanalım using System; public class RefOutExample { public static void Main() { int refValue=5;//başlangıç değeri atanması zorunludur. int outValue;//başlangıç değeri atanması zorunlu değildir. ChangeMethod(out outValue, ref refValue); Console.WriteLine("ChangeMethod'dan sonra refValue : " + refValue); //Output 7 Console.WriteLine("ChangeMethod'dan sonra outValue: " + outValue); //Output 8 } static void ChangeMethod(out int i,ref int j) { i = 8; // i argümanına bir değer atamak zorunludur j = j + 2; // j için böyle bir zorunluluk yoktur } }   Daha çok C - C++ dillerinde etkin bir şekilde kullanılan pass by reference C# dilinde de developer'ların kullanımına sunulmuş. Birden fazla parametre dönmesini istediğimiz metodlar da veya orjinal veri üzerinde method içerisinde işlem yapmak istediğimizde ref ve out keywordlerinden kolayca faydalanabiliriz.

C# Destructor Nedir ?

Destructor kısaca constructor'ın tam tersidir.Constructor için bir nesnenin instance'ı alınırken Ram'de ki Heap bölümünde yer ayırmadan önce çağrılan metod diyebiliriz. Destructor tam bu nesne ram'den silinmeden önce çağrılan metod dur.  Peki neden buna gerek var dersek; garbage collector sağ olsun bizim için ram'de işleri bitmiş nesneleri ram'den siliyor ve bazen tam bu silinme anını bilmek isteriz. Aslında C# tarafında çok fazla ihtiyaç duyulan bir şey değil ancak C-C++ gibi Ram yönetimini developer'a bırakan programlama dillerinde Destructor'a çok fazla ihtiyaç duyuluyordu. C# ram yönetimini tamamiyle developer'a bırakmadığından gerek kalmadıkça bu metodu kullanmıyoruz. Destructor Özellikleri Her class'ın sadece bir tane Destructor'ı olabilir, Destructor tanımlanırken class ismini başına "~" işareti koyulur, Struct'lar için tanımlanamaz, sadece class'lar için tanımlanırlar, Dışarıdan çağrılamaz, otomatik olarak invoke olur, Destructor parametre alamaz. Kalıtım yapılamazlar ve overload edilemezler.   Örnek kullanım olarak; class Person { ~Person() // destructor { // cleanup statements... } } Kullanımı yukarıda olduğu gibidir. Yazım olarak Constructor tanımlar gibi yazıyoruz ancak isminin başına "~" işaretini koyuyoruz.

sealed class nedir

Kalıtım nesneye dayalı programlamada ki en büyük etkendir. Projede tanımladığımız bir class başka bir class veya interface'den ihtiyaca göre inheret olabilir ve böylelikle bir nevi oop'nin faydalarından yararlanmış oluruz. Ancak bazen yazmış olduğumuz bir class'ın başka class'lara kalıtım vermesini istemeyebiliriz. Neden böyle bir şeye ihtiyaç duyalım ki dersek genellikle security konularından dolayı böyle bir durum söz konusu olabilir. C# tarafında bu ihtiyacımızı karşılayacak olan sealed  keyword'ü bulunmaktadır. Eğer bir class sealed tanımlanırsa bu class alt class'lara kalıtım veremez. Örnek olarak ; sealed tanımlı A class'ımız olsun ve 2 tanede sealed olmayan B,C adında class'larımız olsun // Sealed class sealed class A { } public class B { } //Sorunsuz çalışır public class C : B { } //Hata verir !!! cannot derive from sealed type 'A' public class C : A { } C class'ı B class'ından kalıtım alabilirken A class'ından kalıtım alamayacaktır. Çünkü A class'ı sealed'dır ve başka hiçbir class'a kalıtım veremez.  .Net Framework içerisinde bir çok sealed class bulunmaktadır. Bunlardan en tanınmış olanı String class'ı dır. Bu nedenledir ki herhangi bir class String class'ından kalıtım almaya çalıştığında "cannot derive from sealed type 'string'" hatasını verir. 

Smart Home Project

Summary Smart Home project provides users to control the electronic devices via it’s desktop application and mobile application. User can create scenarios which are “Arrive” and “Leave” scenarios and they can create feature events about sensors or electronic devices which are time-based and the system perform these events according to the different device types. All the actions process on the system are logged in the database and reports to the user.     Desktop Application There is a laptop which is connected to the arduino and it receives and sends data from cloud system to arduino board or arduino board to cloud system. Users can access the in time data that comes from arduino board and it is displayed on a page which works on desktop application. They can create “Arrive” and “Leave” scenarios or they can create feature events using that application.     Cloud  In the cloud side all data and necessary files are stored on azure cloud services. All the tables in the database have been developed by using MS-SQL, and using Entity Framework technology insertion, deletion and update operations performed. There is a virtual machine runs on azure and it communicates with mobile application and desktop application the process the commands.         Mobile Application  There is an application which works on Windows Phone operating system. Users who has Windows Phone device can install the application and login. After processing some security functions they can easily display the device status and values of the sensors that are in smart home system.   Use Case Diagram