DECODE : decode( expression , search , result [, search , result]... [, default] ) fonksiyonu if-then-else kullanımına karşılık gelir.CASE .. WHEN ifadesinin aynısıdır. Amaç daha okunabilir kod yazmak olabilir.
SQL> select * from birimler;
BIRIM_KODU...... BIRIM_ADI
---------------------- ---------------
14199........ dahiliye
22897........ cildiye
SQL> select * from muayene;
BIRIM_KODU...... TARIH
---------------------- ---------------
14199 ........ 31-MAY-08
22897 ........ 30-MAY-08
SQL> SELECT m.tarih, MAX (DECODE (b.birim_adi, 'dahiliye', 1, 0)) dahiliye,
2 MAX (DECODE (b.birim_adi, 'cildiye', 1, 0)) cildiye
3 FROM birimler b, muayene m
4 WHERE b.birim_kodu = m.birim_kodu
5 GROUP BY m.tarih;
TARIH....... DAHILIYE......... CILDIYE
----------------- --------------- ----------------
30-MAY-08............ 0 ................. 1
31-MAY-08............ 1 ................. 0
Buradaki max ifadelerini birim sayisina gore ayarlayabiliriz.
07 Ağustos 2008 Perşembe
CASE WHEN...(SORGU İLE TABLO OLUŞTURMAK)
Sorum:
case when ile basit bir tablo oluşturabiliriz;saat bazında birimlerin sayısını tablo biçiminde gösterelim;
tablolar aşağıdaki gibi ;
'birimler' tablosu:
birim_kodu ...... birim_adi
----------- -------------
100200 ......... dahiliye
100250 ......... cildiye
100305 ......... psikiyatri
'muayene' tablosu:
tarih .............. birim
---------- --------------
18.05.2008 08:25:10........ 100200
18.05.2008 08:32:00 ....... 100200
18.05.2008 09:08:45 ....... 100250
18.05.2008 10:15:20 ....... 100305
18.05.2008 10:40:10 ....... 100305
18.05.2008 10:53:02 ....... 100250
----------------------------- ---------
dikkat edilmesi gereken nokta; 'birimler' tablosundaki birim adları sorgu sonucu çıkacak tablomuzda alan isimleri olarak çıkacak ve 'muayene' tablosundaki o birimin o tarihe ait toplam kayıt sayısı sorgu sonucu çıkacak tablomuzda olacak.
select tarih,count(*) --------------
from birimler b join muayene m on(b.birim_kodu=m.birim)
group by m.tarih
acaba nasıl bir sql sorgusu yazılmalı?
Çözüm Yolu:
SELECT TO_CHAR(M.TARIH,'HH24') AS MUAYENE_SAATI,
count(case when M.BIRIM = '100200' then 1 end) as DAHILIYE,
count(case when M.BIRIM = '100250' then 1 end) as CILDIYE,
count(case when M.BIRIM = '100305' then 1 end) as PSIKIYATRI
FROM MUAYENE M JOIN BIRIMLER B ON(M.BIRIM=B.BIRIM_KODU)
WHERE M.BIRIM IN('100200','100250','100305')
AND M.TARIH BETWEEN :T1 AND :T2
GROUP BY TO_CHAR(M.TARIH,'HH24')
ORDER BY TO_CHAR(M.TARIH,'HH24')
tablomuz aşağıdaki gibi satır ve sütunlardan oluşur:
MUAYENE_SAATI.......DAHILIYE ......CILDIYE.......PSIKIYATRI
----------------------- -------------- ------------- -----------------
08:00-09:00 ............ 2 ............ 0 ................ 0
09:00-10:00 ............ 0 ............ 1 ................ 0
10:00-11:00 ............. 0 ............ 1 ............... 2
case when ile basit bir tablo oluşturabiliriz;saat bazında birimlerin sayısını tablo biçiminde gösterelim;
tablolar aşağıdaki gibi ;
'birimler' tablosu:
birim_kodu ...... birim_adi
----------- -------------
100200 ......... dahiliye
100250 ......... cildiye
100305 ......... psikiyatri
'muayene' tablosu:
tarih .............. birim
---------- --------------
18.05.2008 08:25:10........ 100200
18.05.2008 08:32:00 ....... 100200
18.05.2008 09:08:45 ....... 100250
18.05.2008 10:15:20 ....... 100305
18.05.2008 10:40:10 ....... 100305
18.05.2008 10:53:02 ....... 100250
----------------------------- ---------
dikkat edilmesi gereken nokta; 'birimler' tablosundaki birim adları sorgu sonucu çıkacak tablomuzda alan isimleri olarak çıkacak ve 'muayene' tablosundaki o birimin o tarihe ait toplam kayıt sayısı sorgu sonucu çıkacak tablomuzda olacak.
select tarih,count(*) --------------
from birimler b join muayene m on(b.birim_kodu=m.birim)
group by m.tarih
acaba nasıl bir sql sorgusu yazılmalı?
Çözüm Yolu:
SELECT TO_CHAR(M.TARIH,'HH24') AS MUAYENE_SAATI,
count(case when M.BIRIM = '100200' then 1 end) as DAHILIYE,
count(case when M.BIRIM = '100250' then 1 end) as CILDIYE,
count(case when M.BIRIM = '100305' then 1 end) as PSIKIYATRI
FROM MUAYENE M JOIN BIRIMLER B ON(M.BIRIM=B.BIRIM_KODU)
WHERE M.BIRIM IN('100200','100250','100305')
AND M.TARIH BETWEEN :T1 AND :T2
GROUP BY TO_CHAR(M.TARIH,'HH24')
ORDER BY TO_CHAR(M.TARIH,'HH24')
tablomuz aşağıdaki gibi satır ve sütunlardan oluşur:
MUAYENE_SAATI.......DAHILIYE ......CILDIYE.......PSIKIYATRI
----------------------- -------------- ------------- -----------------
08:00-09:00 ............ 2 ............ 0 ................ 0
09:00-10:00 ............ 0 ............ 1 ................ 0
10:00-11:00 ............. 0 ............ 1 ............... 2
DENSE_RANK () OVER (PARTITION BY...
Aşağıda daha önce karşılaştığım bir problem ile ilgili sorum ve çözüm yolları:
Sorum:
'kullanıcı_bilgileri' adlı tablonun içeriği aşağıdaki gibidir;
kul_adi kul_termid kul_tarih
------- ---------- ------------
abulut abc8 03-04-2007
abulut abe5 08-07-2008
abulut abk2 06-05-2008
hsezen dhk1 12-02-2005
hsezen ddk6 10-08-2006
bu tablo kullanılarak yapılacak sorgu sonucu aşağıdaki gibi her kullanıcının en son hangi tarihte hangi terminal id'si ile giriş yaptığı satırın çıkması gerekiyor;
kul_adi kul_termid kul_tarih
---------- ---------- ----------
abulut abe5 08-07-2008
hsezen ddk6 10-08-2006
... .. ..
şeklinde olması lazım.Nasıl bir sorgu yazmam gerekiyor?
SELECT KUL_ADI,KUL_TERMID,MAX(KUL_TARIH)AS SON_TARIH FROM KULLANICI_BILGILERI GROUP BY KUL_ADI,KUL_TERMIDORDER BY KUL_ADI
gibi bi sorgu yaptım ancak farklı terminal id'ler olduğundan onlara göre gruplama yapıyor ve biçok satır çıkıyor...
Çözüm Yolları:
-------------------1.yol
Select * from (
SELECT KUL_ADI,KUL_TERMID,KUL_TARIH ,dense_rank() over(partition by kul_adi order by kul_tarih desc) sira
FROM KULLANICI_BILGILERI
) where sira=1
--------------------2.yol
select k.* from KULLANICI_BILGILERI k,
(select k1.kul_adi, max(k1.kul_tarih) kul_tarih from KULLANICI_BILGILERI k1 group by k1.kul_adi) t
where k.kul_adi=t.kul_adi and k.kul_tarih=t.kul_tarih
-------------------3.yol
select a.* from KULLANICI_BILGILERI a
where a.kul_tarih = (select max(kul_tarih) from KULLANICI_BILGILERI b where b.kul_adi = a.kul_adi)
Sorum:
'kullanıcı_bilgileri' adlı tablonun içeriği aşağıdaki gibidir;
kul_adi kul_termid kul_tarih
------- ---------- ------------
abulut abc8 03-04-2007
abulut abe5 08-07-2008
abulut abk2 06-05-2008
hsezen dhk1 12-02-2005
hsezen ddk6 10-08-2006
bu tablo kullanılarak yapılacak sorgu sonucu aşağıdaki gibi her kullanıcının en son hangi tarihte hangi terminal id'si ile giriş yaptığı satırın çıkması gerekiyor;
kul_adi kul_termid kul_tarih
---------- ---------- ----------
abulut abe5 08-07-2008
hsezen ddk6 10-08-2006
... .. ..
şeklinde olması lazım.Nasıl bir sorgu yazmam gerekiyor?
SELECT KUL_ADI,KUL_TERMID,MAX(KUL_TARIH)AS SON_TARIH FROM KULLANICI_BILGILERI GROUP BY KUL_ADI,KUL_TERMIDORDER BY KUL_ADI
gibi bi sorgu yaptım ancak farklı terminal id'ler olduğundan onlara göre gruplama yapıyor ve biçok satır çıkıyor...
Çözüm Yolları:
-------------------1.yol
Select * from (
SELECT KUL_ADI,KUL_TERMID,KUL_TARIH ,dense_rank() over(partition by kul_adi order by kul_tarih desc) sira
FROM KULLANICI_BILGILERI
) where sira=1
--------------------2.yol
select k.* from KULLANICI_BILGILERI k,
(select k1.kul_adi, max(k1.kul_tarih) kul_tarih from KULLANICI_BILGILERI k1 group by k1.kul_adi) t
where k.kul_adi=t.kul_adi and k.kul_tarih=t.kul_tarih
-------------------3.yol
select a.* from KULLANICI_BILGILERI a
where a.kul_tarih = (select max(kul_tarih) from KULLANICI_BILGILERI b where b.kul_adi = a.kul_adi)
Kaydol:
Kayıtlar (Atom)