Merhaba arkadaşlar,
Gördüğüm kadarıyla hiç araştırma yapmadan bodoslama dalıyoruz kod yazmaya. Nasıl daha iyi kod yazarım nasıl daha iyi verim alırım demiyoruz. O yüzden mysql kullanırken en iyi yolları anlatma gereği duydum. Başlayalım.
1. Mysql yerine Mysqli kullanın.
Mysqli ile sunulan en dikkat çekici yenilikler şu şekildedir;
- Nesne Tabanlı Arabirim
- Ön Hazırlıklı Sorgular
ikisi arasında karşılaştırmaları;
http://kodogren.org/2014/mysql-vs-my...rsilastirmasi/ http://kodogren.org/2014/mysql-vs-mysqli-fonksiyonlari/
ya da google da arama yaparak görebilirsiniz.
2. Kodlarınızı en iyi şekilde optimize edin.
Çoğu Mysql server ında cache leme açıktır. Ama hangi sorgular direk cache e alınır hangisi alınmaz ona dikkat etmemiz gerekir.
Örnek;
// cache e alınmaz
$r = mysqli_query("SELECT ad FROM kullanici WHERE tarih >= CURDATE()");
// cache e alınır
$bugun = date("Y-m-d");
$r = mysqli_query("SELECT ad FROM kullanici WHERE tarih >= '$bugun'");ilk sorgu cache e alınmaz sebebi ise Mysql fonksiyonlarından curdate i kullanmamız. ama aynı işlemi yapan 2. sorguda ise cache alınır bir daha ki sorgulamada Mysql daha hızlı cevap verir.
CURDATE(), NOW(), RAND() gibi fonksiyonlar Mysql in cacheleme özelliğini kullanamamanıza neden olur.
3. Anahtar(key) kullanın.
--ogrenci--
ad --- soyad --- bolum
gibi bir tablonuz varsa primary key ekleyin.
--ogrenci--
id --- ad --- soyad --- bolum
buradaki id primary key olarak eklenmiştir. daha sonra işlem yapmak istediğimizde bu primary key e göre çok rahatlıkla işlem yapabiliriz.
UPDATE, SELECT .... WHERE id = id_degeri
şeklinde işlemlerimiz çok daha basit ve hızlı şekilde çözülecektir.
4. Tek cevap gelecek sorgularda LIMIT 1 kullanın.
Veritabanında aynı kullanıcı adıyla ya da aynı mail adresiyle kayıt yapılmasını çoğumuz engelleriz zaten. peki bu kontrolü yaparken nasıl sorgu yapmamız lazım. Zaten o isimde ya da o mail adresiyle tek sorgu gelecek biliyoruz. O yüzden daha iyi performans için LIMIT 1 ekleyin.
// bunun yerine:
$r = mysqli_query("SELECT id FROM kullanici WHERE ad = '$ad'");
// bunu kullanın
$r = mysqli_query("SELECT id FROM kullanici WHERE ad = '$ad' LIMIT 1");5. Arama yapılacak alanlarda FullText ya da Index(KEY) kullanın.
Aşağıdaki resimde key kullanmadan önce yapılan sorguyla key eklendikten sonraki süreler karşılaştırılmış.
ALTER TABLE 'users' ADD INDEX ('last_name');ALTER TABLE `users` ADD FULLTEXT `fulltextindex` (`last_name`).
Benim tavsiyem fulltext kullanmanız yönündedir.
FullText hakkında daha fazla bilgi almak için google da arama yapabilirsiniz. ya da
bu linke bakabilirsiniz.
6. JOIN işlemlerinde doğru seçimi yapın
Bildiğimiz üzere JOIN işlemi yapmanın 3 farklı yolu var. Bunlar arasından hangisini seçeceğimize dikkat etmemiz lazım. Görüyorum ki herkes LEFT JOIN kullanıyor ama ya işlemlerinizde INNER JOIN daha basit ve daha hızlı olacaksa hiç araştırdınız mı?
LEFT JOIN

RIGHT JOIN

INNER JOIN
3ü arasındaki farkları ve örnekleri bu linklerden görebilirsiniz.
http://www.w3schools.com/sql/sql_join_left.asp http://www.w3schools.com/sql/sql_join_right.asp http://www.w3schools.com/sql/sql_join_inner.asp 7. JOIN işlemlerinde aynı tipleri eşleştirin $r = mysqli_query("SELECT ad FROM kullanici
LEFT JOIN sirket ON (kullanici.il_id = sirket.il_id)
WHERE kullanici.id = $user_id");burada kullanici tablosuyla sirket tablosunu birleştirdik fakat önemli olan konu kullanici tablosundaki il_id INT olup sirket tablosundaki il_id nin FLOAT ya da VARCHAR gibi farklı tiplerde olmamasına dikkat edin.
8. RAND() kullanmaktan kaçının
Sorgularınızda RAND() kullanmak daha çok işinize geliyor biliyorum ama bunun yerine kesinlikle ve kesinlikle php ile random yapmayı deneyin göreceksiniz ki daha hızlı sonuç alacaksınız.
// sakın!!
$r = mysqli_query("SELECT ad FROM kullanici ORDER BY RAND() LIMIT 1");
// onun yerine bunu kullanın
$r = mysqli_query("SELECT count(id) as sayi FROM kullanici");
$d = mysqli_fetch_row($r);
$rand = mt_rand(0,$d['sayi'] - 1);
$r = mysqli_query("SELECT ad FROM kullanici LIMIT $rand, 1");Benim tavsiyem hiç random kullanmama yönünde ama illa kullanacaksanız böyle kullanın.
9. num_rows kullanmaktan kaçının
Sorgularınızda num_rows kullanmak daha çok işinize geliyor biliyorum ama bunun yerine kesinlikle ve kesinlikle COUNT(id) yapmayı deneyin göreceksiniz ki daha hızlı sonuç alacaksınız.
// sakın!!
$r = mysqli_query("SELECT ad FROM kullanici WHERE il = '$il'");
echo mysqli_num_rows($r);
// onun yerine bunu kullanın
$r = mysqli_query("SELECT COUNT(id) as sayi FROM kullanici WHERE il = '$il'");
$d = mysqli_fetch_row($r);
echo $d['sayi'];10. SELECT * kullanmaktan kaçının
Sorgu sırasında almak istediğiniz veriler net olsun. kullanıcının adını mı alıcam sadece adını alın. ad, soyad, bolum, il lazımsa sadece bunları alın.
// yapmayın
$r = mysqli_query("SELECT * FROM kullanici WHERE id = 1");
$d = mysqli_fetch_assoc($r);
echo 'Hoşgeldiniz '.$d['ad'];
// bunu kullanın
$r = mysqli_query("SELECT ad FROM kullanici WHERE id = 1");
$d = mysqli_fetch_assoc($r);
echo 'Hoşgeldiniz '.$d['ad'];11. Primary Key kullanın
Her tablonuzda bir tane primary key olsun çekinmeyin. Tabi primary key kullanırken dikkat etmemiz lazım VARCHAR ya da FLOAT gibi saçma primary keyler belirlemeyin. INT kullanmak her zaman primary keyler için daha iyidir.
id = INT, PRIMARY KEY, AUTO_INCREMENT
hatta UNSIGNED da kullanabilirsiniz negatif değer alamayacak nasılsa.
12. NULL dan kaçının
Çok zor da olmadıkça veritabanlarında NULL değerleri alacak tablo oluşturmaktan kaçının.
Eğer INT ise alan default olarak NULL yerine 0 tanımlayın.
VARCHAR ise default olarak '' tanımlayın.
13. Alanlarınız sabit uzunlukta ve yeterince olsun
Oluşturduğunuz alanlar sabit uzunlukta ve yeterli derecede olsun.
Örneğin sadece 0,1 değeri alacak bi yer için gidipte INT(11) gibi saçma alanlar oluşturmayın. BIT(1) ya da TINYINT(1) yeterli olacaktır.
Text alanlarından mümkünse uzak durun bunun yerine VARCHAR(1024) gibi ne kadar lazımsa o kadar tanımlama yapın.
ip alanlarını tutan alan için gidipte VARCHAR(255) falan kullanmayın, VARCHAR(15) yeterli olacaktır.
14. Büyük sayılarda INSERT ya da DELETE işlemi yapmayın
Sorguları parçalamayı deneyin.
// bunun yerine
mysqli_query("DELETE FROM logs WHERE log_date <= '2009-10-01'");
// bunu kullanın
while (1) {
$r = mysqli_query("SELECT COUNT(id) as sayi FROM logs WHERE log_date <= '2009-10-01'");
$d = mysqli_fetch_row($r);
if ($d['sayi'] > 0)
mysqli_query("DELETE FROM logs WHERE log_date <= '2009-10-01' LIMIT 1000");
else break;
// az bekle
usleep(50000);
}15. Depolama Motorlarını(Storage Engine) doğru kullanın
MyISAM ve InnoDB her ikisininde kendine göre avantajları ya da dezavantajları var. bunları tablonuza göre uygun olup olmadığını kontrol ederek seçiniz.
Eğerki InnoDB kullanmaya karar verdiyseniz burası çok önemli innodb_buffer_pool_size alanını kendinize göre arttırın ya da hostunuza iletin o geri dönüş yapacaktır.
innodb_buffer_pool_size = 256M
Hepsini okuduğunuz için Teşekkür ederim.
Kolay gelsin.
NOT: Konudaki linklerin benimle uzaktan yakından alakası olmayıp konuyu daha iyi kavrayabilmeniz için örnek olarak verilmiştir.
Ayrıca hatalı olduğumu düşünüyorsanız konu altından nedeni ile açıklarsanız ben de bilgilenmiş olurum. Şimdiden teşekkür ederim.