Question

I have a query. I have created index for all joined key, pre-filter the master table and choose specific rows to select, but it still take long time to show(sometimes it hangs). What should We do to improve the performance?

SELECT *
FROM   t_responden a
       INNER JOIN t_kepemilikan_tik b
               ON a.res_id = b.res_id
       INNER JOIN t_televisi c
               ON a.res_id = c.res_id
       INNER JOIN t_telepon_hp d
               ON a.res_id = d.res_id
       INNER JOIN t_radio e
               ON a.res_id = e.res_id
       INNER JOIN t_media_cetak f
               ON a.res_id = f.res_id
       INNER JOIN t_internet g
               ON a.res_id = g.res_id
       LEFT JOIN t_mst_pendidikan n
              ON a.res_pendidikan_kk = n.kd_pendidikan
       LEFT JOIN t_mst_pendidikan o
              ON a.res_pendidikan = o.kd_pendidikan
       LEFT JOIN t_mst_penghasilan p
              ON a.res_penghasilan = p.kd_penghasilan

       LEFT JOIN t_mst_aksesibilitas q
              ON a.res_aksesibilitas = q.kd_akses
       LEFT JOIN t_mst_mobilitas r
              ON a.res_mobilitas = r.kd_mobilitas
       LEFT JOIN t_mst_pekerjaan s
              ON a.res_pekerjaan = s.kode
       LEFT JOIN t_mst_pengeluaran t
              ON a.res_pengeluaran = t.kode

       INNER JOIN t_pernyataan h
               ON a.res_id = h.res_id

       INNER JOIN (SELECT * FROM t_mst_prop WHERE kode IN ( '3200', '1600', '1800', '3600' )) i
               ON a.res_propinsi = i.kode

       INNER JOIN (SELECT * FROM t_mst_kabkota WHERE kode_prop IN ( '3200', '1600', '1800', '3600' )) j
               ON ( a.res_kabkota = j.kode
                    AND a.res_propinsi = j.kode_prop )

       INNER JOIN (SELECT * FROM t_mst_kec WHERE kode_prop IN ( '3200', '1600', '1800', '3600' )) k
               ON ( a.res_kecamatan = k.kode
                    AND a.res_kabkota = k.kode_kabkota
                    AND a.res_propinsi = k.kode_prop )

       INNER JOIN (SELECT * FROM t_mst_desa WHERE kode_prop IN ( '3200', '1600', '1800', '3600' ))l
               ON ( a.res_keldesa = l.kode
                    AND a.res_kabkota = l.kode_kabkota
                    AND a.res_propinsi = l.kode_prop
                    AND l.kode_kec = a.res_kecamatan )

WHERE  a.res_tahunsurvei = 2013
       AND res_propinsi IN ( '3200', '1600', '1800', '3600' )
ORDER  BY 1
Was it helpful?

Solution

SELECT STRAIGHT_JOIN
      *
   FROM   
      t_responden a
         INNER JOIN t_kepemilikan_tik b
            ON a.res_id = b.res_id
         INNER JOIN t_televisi c
            ON a.res_id = c.res_id
         INNER JOIN t_telepon_hp d
            ON a.res_id = d.res_id
         INNER JOIN t_radio e
            ON a.res_id = e.res_id
         INNER JOIN t_media_cetak f
            ON a.res_id = f.res_id
         INNER JOIN t_internet g
            ON a.res_id = g.res_id
         LEFT JOIN t_mst_pendidikan n
            ON a.res_pendidikan_kk = n.kd_pendidikan
         LEFT JOIN t_mst_pendidikan o
            ON a.res_pendidikan = o.kd_pendidikan
         LEFT JOIN t_mst_penghasilan p
            ON a.res_penghasilan = p.kd_penghasilan
         LEFT JOIN t_mst_aksesibilitas q
            ON a.res_aksesibilitas = q.kd_akses
         LEFT JOIN t_mst_mobilitas r
            ON a.res_mobilitas = r.kd_mobilitas
         LEFT JOIN t_mst_pekerjaan s
            ON a.res_pekerjaan = s.kode
         LEFT JOIN t_mst_pengeluaran t
            ON a.res_pengeluaran = t.kode
         INNER JOIN t_pernyataan h
            ON a.res_id = h.res_id

         INNER JOIN t_mst_prop i
            ON a.res_propinsi = i.kode
         INNER JOIN t_mst_kabkota j
               ON  a.res_propinsi = j.kode_prop 
               AND a.res_kabkota = j.kode
         INNER JOIN t_mst_kec k
               ON a.res_propinsi = k.kode_prop
               AND a.res_kecamatan = k.kode
               AND a.res_kabkota = k.kode_kabkota
         INNER JOIN t_mst_desa l
               ON  a.res_propinsi = l.kode_prop
               AND a.res_keldesa = l.kode
               AND a.res_kabkota = l.kode_kabkota
               AND a.res_kecamatan = l.kode_kec
   WHERE  
          a.res_tahunsurvei = 2013
      AND a.res_propinsi IN ( '3200', '1600', '1800', '3600' )
   ORDER BY 
      1

You should have an index on your t_responden table ON ( res_tahunsurvei, res_propinsi) to match your where qualification criteria. Additionally, all your inner joins to the other tables where you are applying the IN via sub-selects is killing you. You are already limiting on the "kode"s in the where, so if you apply that as your join you should be good.

Additionally, since all the other tables appear to be more "lookup", I've added "STRAIGHT_JOIN" to tell MySQL to query in the order the tables you have listed

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top