Ana içeriğe geç
Kesit SQL
Orta · Fonksiyonlar

Veri tipleri ayrıntılı: ondalık hassasiyet, Unicode metin ve saat dilimleri

FLOAT ile DECIMAL farkı, NVARCHAR ve N'..', DATE/DATETIME/TIMESTAMP, AT TIME ZONE.

Uygulamada aç, 9 alıştırmayı çözÜcretsiz, hesap gerekmez, kurulum yok.

Bu sayfa dersin okuma sürümüdür. Metin bir kutuyu çalıştırmanı ya da adıma geçmeni söylüyorsa dersi uygulamada aç.

Para FLOAT'ta tutulmaz

FLOAT/REAL/DOUBLE ikili kayan noktalı sayılardır; 0,1 gibi değerleri tam saklayamazlar. Küçük farklar toplamlarda büyür ve = karşılaştırmaları şaşırtıcı sonuç verir.

SELECT CAST(0.1 AS FLOAT) + CAST(0.2 AS FLOAT) AS toplam,
       CASE WHEN CAST(0.1 AS FLOAT) + CAST(0.2 AS FLOAT) = CAST(0.3 AS FLOAT) THEN 'eşit' ELSE 'eşit değil' END AS karsilastirma;

Tipi açıkça FLOAT yazdık, çünkü 0.1 gibi ondalık sabitler PostgreSQL, SQL Server, MySQL ve Oracle'da kesin türdedir: orada 0.1 + 0.2 = 0.3 doğru çıkar. Sorun sütun ya da ifade kayan noktalı olduğunda başlar. Bu örnekteki eşitsizliği PostgreSQL'de gerçek motorda doğruladık. Bu uygulamanın motoru SQLite olduğu için burada sabitler de kayan noktalı çalışır; bu, taklidin bilinen sınırlarından biridir.

İhtiyaçTip
Para, miktar, oranDECIMAL(p,s) / NUMERIC(p,s) (SQL Server'da MONEY da var ama hesaplamada yuvarlama riski nedeniyle DECIMAL önerilir; BigQuery'de NUMERIC)
Ölçüm, bilimsel değerFLOAT / DOUBLE PRECISION / FLOAT64
Sayaç, kimlikINT, büyükse BIGINT (SQL Server INT sınırı ≈ 2,1 milyar)
Evet/hayırBIT (SQL Server), BOOLEAN (PostgreSQL, MySQL), BOOL (BigQuery); Oracle'da 23ai öncesi NUMBER(1)
KuralOndalıklı değerleri karşılaştırırken eşitlik yerine fark kullan: ABS(a - b) < 0.0001. Raporlarda yuvarlamayı en sonda yap.

Metin: uzunluk ve Unicode

SELECT name, LENGTH(name) AS karakter
FROM products
WHERE name LIKE '%ş%' OR name LIKE '%ğ%' OR name LIKE '%ı%';

Tarih ve saat tipleri

Yalnız tarihTarih + saat (bölgesiz)Saat dilimli an
SQL ServerDATEDATETIME2 (DATETIME eski)DATETIMEOFFSET
PostgreSQLDATETIMESTAMPTIMESTAMPTZ (UTC saklar, oturumun saat diliminde gösterir)
MySQLDATEDATETIMETIMESTAMP (UTC'ye çevirip saklar)
OracleDATE (saat de içerir!)TIMESTAMPTIMESTAMP WITH TIME ZONE
BigQueryDATEDATETIMETIMESTAMP (her zaman UTC an)

Saat dilimleri

Altın kural: anları UTC olarak sakla, kullanıcıya gösterirken yerel saate çevir. Türkiye 2016'dan beri yaz-kış saati uygulamadan UTC+3'tür ama müşterilerin veya sunucuların başka bölgelerde olabileceğini unutma.

-- SQL Server
SELECT CAST('2024-11-29 21:30:00' AS DATETIME2) AT TIME ZONE 'UTC' AT TIME ZONE 'Turkey Standard Time' AS istanbul;
SELECT SYSUTCDATETIME() AS utc_simdi, SYSDATETIMEOFFSET() AS yerel_simdi;

-- PostgreSQL
SELECT TIMESTAMPTZ '2024-11-29 21:30:00+00' AT TIME ZONE 'Europe/Istanbul' AS istanbul;
SET TIME ZONE 'Europe/Istanbul';

-- MySQL (saat dilimi tabloları yüklüyse)
SELECT CONVERT_TZ('2024-11-29 21:30:00', 'UTC', 'Europe/Istanbul');

-- Oracle
SELECT FROM_TZ(TIMESTAMP '2024-11-29 21:30:00', 'UTC') AT TIME ZONE 'Europe/Istanbul' FROM dual;

-- BigQuery
SELECT DATETIME(TIMESTAMP '2024-11-29 21:30:00+00', 'Europe/Istanbul') AS istanbul;
Gün sınırıUTC'de saklanan olayları “günlük” raporlarken yerel saate çevirmeden DATE(event_time) alırsan, Türkiye için 00:00–03:00 arasındaki olaylar bir önceki güne yazılır.

Bu uygulamadaki web_events.event_time değerlerini UTC kabul edip İstanbul saatine çevirelim (+3 saat):

SELECT event_time AS utc,
       datetime(event_time, '+3 hours') AS istanbul,
       date(event_time) AS utc_gun,
       date(datetime(event_time, '+3 hours')) AS istanbul_gun
FROM web_events
WHERE strftime('%H', event_time) IN ('21', '22', '23')
ORDER BY event_id
LIMIT 5;
Alıştırmalara geç (9)