SQL'de iş mantığını kullanıcı tanımlı fonksiyonlar (User Defined Functions, UDF) aracılığıyla gerçekleştirerek hesaplamaların ve iş kurallarının bir kısmını veritabanına taşımak mümkündür.
Skalar fonksiyonlar tek bir değer döndürür ve ifadelerde çağrılır — örneğin, parametrelere dayanarak bir sonuç hesaplamak için:
CREATE FUNCTION dbo.GetDiscount(@price DECIMAL(10,2), @loyaltyLevel INT) RETURNS DECIMAL(10,2) AS BEGIN RETURN @price * CASE WHEN @loyaltyLevel = 1 THEN 0.95 WHEN @loyaltyLevel = 2 THEN 0.90 ELSE 1.0 END END; -- Kullanım örneği: SELECT Name, dbo.GetDiscount(Price, LoyaltyLevel) AS DiscountPrice FROM Products;
Tablo fonksiyonları bir dizi satır (tablo) döndürür:
CREATE FUNCTION dbo.ActiveOrders(@userId INT) RETURNS TABLE AS RETURN ( SELECT * FROM Orders WHERE UserId = @userId AND Status = 'Active' ); -- Kullanım: SELECT * FROM dbo.ActiveOrders(123);
Farklar, kısıtlamalar ve öneriler:
INLINE tablo fonksiyonu ile çoklu ifadeli (multi-statement) tablo fonksiyonu arasındaki fark nedir? Bu seçim performansı nasıl etkiler?
Cevap ve örnek:
-- INLINE CREATE FUNCTION dbo.InlineActiveOrders(@userId INT) RETURNS TABLE AS RETURN ( SELECT * FROM Orders WHERE UserId = @userId AND Status = 'Active' ); -- Çoklu İfadeli CREATE FUNCTION dbo.MultiActiveOrders(@userId INT) RETURNS @result TABLE (...) AS BEGIN INSERT INTO @result SELECT ... -- mantık RETURN END
Tarih
Proje: Finansal Analiz.
Büyük bir tablo kümesine yönelik rapor sorgusunun select kısmında skalar UDF'ler kullandık: SELECT Amount, dbo.CalcTax(Amount, Type) FROM Transactions. Sorgu, satır bazında UDF işlenmesi nedeniyle 5-10 dakika sürdü. Bunu yerleşik CASE ile yeniden yazdık: süre saniyelere düştü.
Tarih
Proje: E-ticaret. Kullanıcı sepetlerini bulmak için çoklu ifadeli tablo fonksiyonları kullandık, burada birden fazla aşamadan oluşan filtreleme mantığı vardı. SQL'in optimal bir plan oluşturmadığını ve gerektiğinde bile tarama yaptığını gördük. INLINE fonksiyonuna geçiş, sorguları 50 kat hızlandırdı.
Tarih
Proje: CRM. Bonus hesaplama iş mantığını karmaşık bir UDF'ye taşıdık. Birkaç ay sonra iş kurallarının değiştiğini anladık, fakat fonksiyonu güncellemek verilerle olan sıkı bağlantı nedeniyle zordu. İteratif bir üründe UDF, backend ve DB arasında değişiklik koordinasyonu için yüksek maliyetlere sebep oldu.