Yanıtlar:
LINQ to SQL, sizi sınıf başına tablo modelini kullanmaya zorlar. Bu kalıbı kullanmanın faydaları, hızlı ve kolay uygulanması ve etki alanınızı mevcut bir veritabanı yapısına dayalı olarak çalıştırmanın çok az çaba gerektirmesidir. Basit uygulamalar için bu tamamen kabul edilebilir (ve çoğu zaman tercih edilir), ancak daha karmaşık uygulamalar için geliştiriciler genellikle bunun yerine alan odaklı bir tasarım modeli kullanmayı önerirler (NHibernate bunu kolaylaştırır).
Sınıf başına tablo modelindeki sorun, veritabanı yapınızın alan tasarımınız üzerinde doğrudan bir etkiye sahip olmasıdır. Örneğin, bir müşterinin birincil adres bilgilerini tutmak için aşağıdaki sütunlara sahip bir Müşteriler tablonuz olduğunu varsayalım:
Şimdi, müşterinin posta adresi için de sütunlar eklemek istediğinizi varsayalım, böylece aşağıdaki sütunları Müşteriler tablosuna eklersiniz:
LINQ to SQL kullanıldığında, etki alanınızdaki Müşteri nesnesi artık bu sekiz sütunun her biri için özelliklere sahip olacaktır. Ancak, etki alanına dayalı bir tasarım modelini izliyor olsaydınız, muhtemelen bir Adres sınıfı oluşturmuş olurdunuz ve Müşteri sınıfınızın biri posta adresi ve diğeri de geçerli adresleri için olmak üzere iki Adres özelliği bulundururdunuz.
Bu basit bir örnek, ancak sınıf başına tablo modelinin nasıl biraz kokulu bir alana yol açabileceğini gösteriyor. Sonunda, size kalmış. Yine, yalnızca temel CRUD (oluşturma, okuma, güncelleme, silme) işlevselliğine ihtiyaç duyan basit uygulamalar için LINQ to SQL, basitlik nedeniyle idealdir. Ama şahsen NHibernate'i kullanmayı seviyorum çünkü daha temiz bir alanı kolaylaştırıyor.
Düzenleme: @lomaxx - Evet, kullandığım örnek basitti ve LINQ to SQL ile iyi çalışacak şekilde optimize edilebilirdi. Noktayı eve götürmeyi mümkün olduğunca basit tutmak istedim. Veritabanı yapınızın etki alanı yapınızı belirlemesinin kötü bir fikir olacağı veya en azından yetersiz OO tasarımına yol açacağı birkaç senaryo var.
Şimdiye kadar kaçırılan iki nokta:
LINQ to SQL, Oracle veya SqlServer dışında herhangi bir veritabanı ile çalışmaz. Bununla birlikte, üçüncü taraflar Oracle için daha iyi destek sunar, örneğin devArt'ın dotConnect , DbLinq , Mindscape'in LightSpeed ve ALinq . (Bunlarla herhangi bir kişisel deneyimim yok)
Linq to NHibernate , Linq'i bir Nhiberate ile kullanmanıza izin verir, bu nedenle kullanmama nedenini ortadan kaldırabilir.
Ayrıca Nhibernate'in yeni akıcı arayüzü, Nhibernate'in eşlemesini yapılandırmayı daha az zahmetli hale getiriyor gibi görünüyor. (Nhibernate'in acı noktalarından birinin kaldırılması)
Güncelleme
Linq to Nhiberate, artık alfa sürümünde olan Nhiberate v3'te daha iyidir . Görünüşe göre Nhiberate v3 bu yılın sonuna doğru gönderilebilir.
Varlık Çerçeve .net 4 itibariyle de gerçek seçenek gibi görünmeye başlıyor.
@Kevin: Sunduğunuz örnekteki sorunun kötü bir veritabanı tasarımı kullanmanız olduğunu düşünüyorum. Bir müşteri tablosu ve bir adres tablosu oluşturup tabloları normalleştireceğini düşünürdüm. Bunu yaparsanız, önerdiğiniz senaryo için kesinlikle Linq To SQL'i kullanabilirsiniz. Scott Guthrie'nin Linq To SQL kullanımı üzerine harika bir yazı dizisi var, bunlara göz atmanızı şiddetle tavsiye ederim.
Linq ve NHibernate'in birbirlerini tamamladığını söyleyebileceğinizi sanmıyorum, çünkü bu, birlikte kullanılabilecekleri anlamına gelir ve bu mümkün olsa da, birini seçip ona bağlı kalmanız çok daha iyi.
NHibernate, veritabanı tablolarınızı etki alanı nesnelerinizle oldukça esnek bir şekilde eşlemenize olanak tanır. Ayrıca, veritabanını sorgulamak için HBL kullanmanıza da olanak tanır.
Linq to SQL ayrıca etki alanı nesnelerinizi veritabanına eşlemenizi sağlar, ancak veritabanını sorgulamak için Linq sorgu sözdizimini kullanır.
Buradaki temel fark, Linq sorgu sözdiziminin, sorgularınızın geçerli olduğundan emin olmak için derleyici tarafından derleme zamanında kontrol edilmesidir.
Linq ile bilinmesi gereken bazı şeyler, sadece .net 3.x'te mevcut olması ve sadece VS2008'de destekleniyor olmasıdır. NHibernate, 2.0 ve 3.x ve VS2005'te mevcuttur.
NHibernate ile bilinmesi gereken bazı şeyler, etki alanı nesnelerinizi veya eşleme dosyalarını oluşturmamasıdır. Bunu elle yapmanız gerekiyor. Linq
bunu sizin için otomatik olarak yapabilir .
Fluent NHibernate, eşleme dosyalarınızı basit kurallara göre oluşturabilir. XML yazma yok ve güçlü bir şekilde yazılmış.
Son zamanlarda, performans nedenleriyle Linq'ten SQL'e NHibernate'e geçmemiz gereken bir proje üzerinde çalıştım. Özellikle L2S'nin nesneleri gerçekleştirme yöntemi NHibernate'in aynısından daha yavaş görünüyor ve değişiklik yönetimi de oldukça yavaş. Ve ihtiyaç duyulmayan belirli senaryolar için değişiklik yönetimini kapatmak zor olabilir.
Varlıklarınızı DataContext ile bağlantısı kesilmiş olarak kullanacaksanız - örneğin WCF senaryolarında - değişiklikleri güncellemek için onları DataContext'e yeniden bağlamada çok fazla sorun yaşayabilirsiniz. NHibernate ile bu konuda hiçbir sorun yaşamadım.
L2S'den özleyeceğim şey, çoğunlukla, varlıkların her iki ucundaki ilişkileri güncel tutan kod üretme. Ama sanırım NHibernate'in bunu orada yapması için bazı araçlar var ...
.ObjectTrackingEnabled = false
senin üzerinde DataContext
yaptığınız değişiklik izleme sorunu çözülmüş olurdu. İş birimi modelini satın aldığınız ve DDD yapmak istemediğiniz sürece, Linq-to-SQL gerçekten bunu sağlar.
"LINQ" ile ne demek istediğini açıklayabilir misin?
LINQ bir veri erişim teknolojisi değildir, yalnızca yerel bir yapı olarak sorgulamayı destekleyen bir dil özelliğidir. Belirli arayüzleri (örneğin IQueryable) destekleyen herhangi bir nesne modelini sorgulayabilir.
Birçok kişi LINQ To SQL'e LINQ olarak başvurur, ancak bu hiç de doğru değildir. Microsoft, .NET 3.5 SP1 ile LINQ To Entities'i piyasaya sürdü. Ek olarak, NHibernate bir LINQ arayüzüne sahiptir, bu nedenle verilerinize ulaşmak için LINQ ve NHibernate'i kullanabilirsiniz.
LINQ derken, LINQ to SQL'i kastettiğinizi varsayıyorum çünkü LINQ, kendisiyle ilişkili bir veritabanı "devam ediyor" değildir. Bu sadece SQL gibi görünmesini sağlamak için bir sürü sözdizimi şekeri içeren bir sorgu dilidir.
Temel örneklerde, NHibernate ve LINQ to SQL aynı problemi çözüyor gibi görünüyor. Geçtikten sonra, NHibernate'in gerçekten zengin alan modelleri oluşturmanıza izin veren birçok özelliği desteklediğini kısa sürede fark edeceksiniz. Ayrıca, LINQ to SQL'i kullandığınız gibi NHibernate'i sorgulamak için LINQ kullanmanıza izin veren bir LINQ to NHibernate projesi de vardır.
Öncelikle iki farklı şeyi ayıralım: Veritabanı modellemesi verilerle ilgilenirken, nesne modelleme varlıklar ve ilişkilerle ilgilenir.
Linq-SQL avantajı, aktif kayıt nesneleri olarak kullanılabilmeleri için veritabanı şemasından hızlı bir şekilde sınıflar oluşturmaktır (bkz. Aktif kayıt tasarım modeli tanımı).
NHibernate avantajı, nesne modellemeniz ve veritabanı modellemeniz arasında esneklik sağlamaktır. Veritabanı, örneğin performans dikkate alınarak verilerinizi en iyi şekilde yansıtacak şekilde modellenebilir. Nesne modellemeniz, Etki Alanına Dayalı Tasarım gibi bir yaklaşım kullanarak iş kuralının öğelerini en iyi şekilde yansıtır. (Kevin Pang yorumuna bakın)
Zayıf modelleme ve / veya adlandırma kurallarına sahip eski veritabanlarında, Linq-to-SQL bu istenmeyen yapıları ve isimleri sınıflarınıza yansıtacaktır. Ancak NHibernate, bu karışıklığı veri eşleştiricilerle gizleyebilir.
Veritabanlarının iyi bir adlandırma ve düşük karmaşıklığa sahip olduğu sıfırdan projelerde, Linq-to-SQL iyi bir seçim olabilir.
Ancak, aynı amaç için otomatik eşlemelerle Fluent NHibernate'i kural olarak haritalama ile kullanabilirsiniz. Bu durumda, XML veya C # içeren herhangi bir veri eşleştiricisi hakkında endişelenmezsiniz ve NHibernate'in, özelleştirebileceğiniz bir kurala dayalı olarak varlıklarınızdan veritabanı şeması oluşturmasına izin verirsiniz.
Öte yandan, Linq-to-SQL öğrenme eğrisi NHibernate'ten daha küçüktür.
Veya Castle ActiveRecords projesini kullanabilirsiniz. Eski bir proje için yeni bir kod geliştirmek için kısa bir süredir kullanıyorum. NHibernate kullanıyor ve aktif kayıt kalıbı üzerinde çalışıyor (bildiğim adı verilen şaşırtıcı). Denemedim, ancak bir kez kullandıktan sonra, doğrudan NHibernate desteğine geçme ihtiyacı hissederseniz, projenizin bir kısmı veya tamamı için bunu yapmak çok fazla olmaz.
Siz "ikisini de kullanmamış bir kişi için" yazdığınız gibi LINQ to SQL'in kullanımı kolaydır, bu nedenle herkes onu kolayca kullanabilir. Ayrıca çoğu zaman yardımcı olan prosedürleri de destekler. Birden fazla tablodan veri almak istediğinizi varsayalım, ardından bir prosedür yazıp bu prosedürü tasarımcıya sürükleyin ve sizin için her şeyi oluşturacaktır. Prosedür adınızın "CUSTOMER_ORDER_LINEITEM" olduğunu ve bu üç tablodan da kayıt aldığını varsayalım, sonra sadece yazın
MyDataContext db = new MyDataContext();
List<CUSTOMER_ORDER_LINEITEMResult> records = db.CUSTOMER_ORDER_LINEITEM(pram1, param2 ...).ToList<CUSTOMER_ORDER_LINEITEMResult>();
NHibernate tarafından desteklenmeyen foreach döngüsünde kayıt nesnenizi de kullanabilirsiniz