Arsip: Bewara SQL for maniak 2

 
user image
more 12 years ago

kaka-delphi

Setelah bro ImanD sukses dengan Bewara SQL for maniak-nya, sekarang saya punya permasalahan yang sama mengenai perintah SQL ini, makanya saya kasih judul Bewara SQL for maniak 2 :lol: Oke ... langsung aja ... ( Maaf, datannya tidak bisa semua ditampilkan disini takut kepanjangan, saya lampirkan aja disini. DB Engine yang saya gunakan adalah MySQL versi 5.1 ) saya punya data sumber seperti ini:

12
5
5
5
5
5
5
5
5
5
5
4
4
5
5
5
5
5
5
5
5
6
7
7
7
8
9
10
11
6
6
6
6
6
6
6
6
6
6
4
4
1
1
1
1
2
2
2
2
1
1
1
1
1
1
1
1
1
1
2
2
4
4
4
4
4
4
4
4
4
4
2
2
2
2
3
3
3
3
1
dari data tersebut setelah di sorting, ingin dibagi-bagi menjadi beberapa kelompok. 1 Kelompok paling banyak terdiri dari 8 data (kelipatan 8 ). Contohnya apabila data "1" ada 16, maka akan menjadi seperti berikut : [sql:1:86605de86b] No Peringkat == ========= 1 8 1 7 1 6 1 5 1 4 1 3 1 2 1 1 1 8 1 7 1 6 1 5 1 4 1 3 1 2 1 1 [/sql:1:86605de86b] Apabila datanya kurang dari 8 : [sql:1:86605de86b] No Peringkat == ========= 2 5 2 4 2 3 2 2 2 1 [/sql:1:86605de86b] Apabila tidak pas pada kelipatan 8: [sql:1:86605de86b] No Peringkat == ========= 3 8 3 7 3 6 3 5 3 4 3 3 3 2 3 1 3 5 3 4 3 3 3 2 3 1 [/sql:1:86605de86b] Hasil yang lengkap dapat di lihat pada lampiran :D Setelah melakukan eksperimen dengan bro reminder2k1[/b:86605de86b] dan [b:86605de86b]manz_delphi, maka dihasilkanlah beberapa query. Tetapi Query berikut yang mendekati kenyataan ... :D : [sql:1:86605de86b] SELECT L.No, if(MOD(L.rowID,8)=0, mod(L.rowID,8)+8, mod(L.rowID,8)) AS Peringkat FROM ( SELECT TT.No, IF(@row>=( SELECT COUNT(*) FROM tb_sem AS T WHERE TT.No = T.No GROUP BY T.No), @row:=1, @row := @row + 1) AS rowID FROM ( SELECT @row:=0) AS r, tb_sem AS TT) AS L ORDER BY L.No, L.rowID [/sql:1:86605de86b] result yang dihasilkan dari query diatas adalah sebagai berikut : [sql:1:86605de86b] No Peringkat == ========= 1 1 1 2 1 3 1 4 1 5 1 6 1 7 1 8 1 1 1 2 1 3 1 4 1 5 1 6 1 7 2 1 2 2 2 3 2 4 2 5 2 6 2 7 2 8 2 1 2 2 3 1 3 2 3 3 3 4 4 1 4 2 4 3 4 5 4 6 4 7 4 8 4 1 4 2 4 3 4 4 4 5 4 6 4 7 5 1 5 2 5 4 5 5 5 6 5 7 5 8 5 1 5 2 5 3 5 4 5 5 5 6 5 7 5 8 5 1 5 2 5 3 6 1 6 3 6 4 6 5 6 6 6 7 6 8 6 1 6 2 6 3 6 4 7 2 7 3 7 4 8 1 9 1 10 1 11 1 12 1 [/sql:1:86605de86b] Sudah melakukan pengelipatan 8, tetapi peringkatnya masih Asceding, belum seperti keinginan. Kira2 dimana yach letak kesalahannya .... ? :? apa ada ide lain .... ? :idea:
user image
more 12 years ago

_lmz

struktur tabel: tb_sem ( no integer ); t1000 ( n integer ); isi tb_sem seperti input. isi t1000 adalah angka dari 1 sampai 1000. jawaban (syntax postgres):

select t.no,
--t.n as maxx, (t1000.n - 1) as rownum,
--(t1000.n - 1) % 8 as modx, (t1000.n - 1) / 8 as divx,
--(((t1000.n - 1) / 8) = ((t.n - 1) / 8)) as is_last,
case when (((t1000.n - 1) / 8) = ((t.n - 1) / 8))
then
(t.n % 8) - ((t1000.n - 1) % 8)
else
8 - ((t1000.n - 1) % 8)
end as rank from
(select no, count(*) as n from tb_sem group by no) as t,
t1000
where t1000.n <= t.n
order by t.no, t1000.n;
uncomment beberapa baris itu untuk melihat sedikit cara kerjanya :). Yang banyak -1 nya itu mungkin bisa dikurangi dengan membuat t1000 mulai dari 0 atau semacamnya...
user image
more 12 years ago

_lmz

Berikut cara kerjanya untuk angka 1 yang ada 15. 1. datanya perlu diberi nomor urut sehingga kita tahu ini angka 1 yang ke-1, ini angka 1 yang ke-2 dst. datanya "dilipat" dengan group by kemudian "dibuka" menggunakan join dengan t1000 sehingga menghasilkan seperti ini: [sql:1:ba07ca3430] select t.no, t1000.n from (select no, count() as maxx from tb_sem group by no) as t, t1000 where t1000.n <= t.maxx order by 1, 2; no | n ----+---- 1 | 1 1 | 2 1 | 3 1 | 4 1 | 5 1 | 6 1 | 7 1 | 8 1 | 9 1 | 10 1 | 11 1 | 12 1 | 13 1 | 14 1 | 15 ... [/sql:1:ba07ca3430] 2. sekarang perlu dipisah menjadi delapan. mod kelihatannya sesuai untuk tujuan ini. [sql:1:ba07ca3430] select t.no, t1000.n, ((t1000.n - 1) % 8) as n_mod from (select no, count( ) as maxx from tb_sem group by no) as t, t1000 where t1000.n <= t.maxx order by 1, 2; no | n | n_mod ----+----+------- 1 | 1 | 0 1 | 2 | 1 1 | 3 | 2 1 | 4 | 3 1 | 5 | 4 1 | 6 | 5 1 | 7 | 6 1 | 8 | 7 1 | 9 | 0 1 | 10 | 1 1 | 11 | 2 1 | 12 | 3 1 | 13 | 4 1 | 14 | 5 1 | 15 | 6 .... [/sql:1:ba07ca3430] sekarang kelihatannya gampang untuk menghasilkan peringkatnya. Untuk deret n_mod bernilai 0..7 pertama maka peringkat hanyalah 8 - n_mod, tetapi untuk deret kedua (0..6) maka peringkat harusnya 7 - n_mod (menjadi 7..1). 3. Kita amati bahwa satu-satunya deret yang n_modnya tidak berjalan dari 0..7 adalah deret terakhir dan itu bisa dideteksi :). Pertama-tama deret itu dapat diberi nomor yaitu dari hasil div: [sql:1:ba07ca3430] select t.no, t1000.n, ((t1000.n - 1) % 8) as n_mod, ((t1000.n - 1) / 8) as n_div from (select no, count() as maxx from tb_sem group by no) as t, t1000 where t1000.n <= t.maxx order by 1, 2; no | n | n_mod | n_div ----+----+-------+------- 1 | 1 | 0 | 0 1 | 2 | 1 | 0 1 | 3 | 2 | 0 1 | 4 | 3 | 0 1 | 5 | 4 | 0 1 | 6 | 5 | 0 1 | 7 | 6 | 0 1 | 8 | 7 | 0 1 | 9 | 0 | 1 1 | 10 | 1 | 1 1 | 11 | 2 | 1 1 | 12 | 3 | 1 1 | 13 | 4 | 1 1 | 14 | 5 | 1 1 | 15 | 6 | 1 ... [/sql:1:ba07ca3430] deret terakhir adalah deret yang nomornya ((n - 1) div 8 ) sama dengan ((n - 1) div 8 ) untuk n terbesar. Tapi kita juga tahu bahwa n terbesar itu adalah count( ) dari tb_sem untuk no tertentu --> kolom t.maxx. Maka apabila deret terakhir, peringkatnya bukan 8 - n_mod tetapi (jumlah elemen dalam deret terakhir) - n_mod. Karena deret terakhir adalah sisa, maka jumlah elemennya adalah t.maxx mod 8. [sql:1:ba07ca3430] select t.no, t1000.n, ((t1000.n - 1) % 8) as n_mod, ((t1000.n - 1) / 8) as n_div, ((t.maxx - 1) / 8) as max_n_div, ( ((t1000.n - 1) / 8) = ((t.maxx - 1) / 8) ) as is_last, case when ( ((t1000.n - 1) / 8) = ((t.maxx - 1) / 8) ) then -- deret terakhir (t.maxx % 8) - ((t1000.n - 1) % 8) else -- bukan terakhir 8 - ((t1000.n - 1) % 8) end as peringkat from (select no, count(*) as maxx from tb_sem group by no) as t, t1000 where t1000.n <= t.maxx order by 1, 2; no | n | n_mod | n_div | max_n_div | is_last | peringkat ----+----+-------+-------+-----------+---------+----------- 1 | 1 | 0 | 0 | 1 | f | 8 1 | 2 | 1 | 0 | 1 | f | 7 1 | 3 | 2 | 0 | 1 | f | 6 1 | 4 | 3 | 0 | 1 | f | 5 1 | 5 | 4 | 0 | 1 | f | 4 1 | 6 | 5 | 0 | 1 | f | 3 1 | 7 | 6 | 0 | 1 | f | 2 1 | 8 | 7 | 0 | 1 | f | 1 1 | 9 | 0 | 1 | 1 | t | 7 1 | 10 | 1 | 1 | 1 | t | 6 1 | 11 | 2 | 1 | 1 | t | 5 1 | 12 | 3 | 1 | 1 | t | 4 1 | 13 | 4 | 1 | 1 | t | 3 1 | 14 | 5 | 1 | 1 | t | 2 1 | 15 | 6 | 1 | 1 | t | 1 [/sql:1:ba07ca3430]
user image
more 12 years ago

reminder2k1

kok sepi amir sih???
user image
more 12 years ago

ImanD

pada kemana yach yg katanya jawara2 SQL(@saysansay, @cyber_hecker n @All), xixixixiix! @reminder2k1 tar postingnya nunggu rame dulu, wakakkakakaka!
user image
more 12 years ago

reminder2k1

wokey bro... :mrgreen:
user image
more 12 years ago

reminder2k1

Nih bro, gw ulik2 lagi dari kasus yg dulu... Moga ini bisa bantu... :mrgreen:
SELECT L.No, L.Peringkat
FROM (SELECT L.No, (L.rowId-1) div 8 AS HasilDiv,
IF(MOD(L.rowID,8)=0,8,MOD(L.rowID,8)) AS Peringkat
FROM (SELECT L.No, L.RowID
FROM (SELECT TT.No, IF(@row>=(SELECT COUNT(No)
FROM tb_sem2 AS T
WHERE TT.No = T.No
GROUP BY T.No
ORDER BY T.No), @row:=1, @row := @row + 1) AS rowID
FROM (SELECT @row:=0) AS r, tb_sem2 AS TT
ORDER BY 1,2) AS L) AS L) AS L
ORDER BY L.No ASC, L.HasilDiv ASC, L.Peringkat DESC
user image
more 12 years ago

_lmz

Hmm, ternyata kalau jumlahnya habis dibagi 8 maka hasilnya salah karena jumlah group terakhir dimod 8 menjadi 0... fix: [sql:1:d5b5519410] case when ( ((t1000.n - 1) / 8) = ((t.maxx - 1) / 8) ) and not (t.maxx % 8 = 0) then -- deret terakhir (t.maxx % 8) - ((t1000.n - 1) % 8) else -- bukan terakhir 8 - ((t1000.n - 1) % 8) end as peringkat [/sql:1:d5b5519410]
more ...
  • Pages:
  • 1
Share to

Random Topic

Local Business Directory, Search Engine Submission & SEO Tools FreeWebSubmission.com SonicRun.com