select при 100.000 строк в таблице.

Discussion in 'PHP' started by rcc0023, 10 Apr 2009.

  1. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    Можно каким нибудь хитроумным запросом брать из такой таблицы со скоростью, как при запросе в маленькую таблицу?
     
  2. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    То есть есть большая таблица, 100.000 строк. Определенные записи запросом:
    $q=mysql_fetch_array(mysql_query('SELECT * FROM '.$table.' WHERE user_id='.$g['user_id'].' LIMIT 1'));
    грузятся очень долго...
     
  3. Forcer

    Forcer Elder - Старейшина

    Joined:
    12 Apr 2007
    Messages:
    321
    Likes Received:
    98
    Reputations:
    12
    таблица проиндексирована?
     
    1 person likes this.
  4. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    да!
     
  5. Gifts

    Gifts Green member

    Joined:
    25 Apr 2008
    Messages:
    2,494
    Likes Received:
    807
    Reputations:
    614
    Вопрос - столь ли необходимо читать все 100к записей?

    И, эээ, зачем делать 100к запросов, логично что они будут тормозить.

    PHP:
    $query=mysql_query('SELECT * FROM '.$table.' WHERE 1');

    while (
    $row=mysql_fetch_array($query))
    {
    print_r($row);
    }
     
    _________________________
  6. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    Так я от туда беру максимум 30 записей... но выводятся они от 5ти секунд, бывает и все 10.

    хотелось бы услышать о выборке одной определенной строки..
     
  7. Gifts

    Gifts Green member

    Joined:
    25 Apr 2008
    Messages:
    2,494
    Likes Received:
    807
    Reputations:
    614
    rcc0023 Вы просто пытаетесь нивелировать достоинства мускуля

    PHP:
    // Сам запрос один штука
    // Например выведем все строки, для user_id между 20 и 30
    $query=mysql_query('SELECT * FROM '.$table.' WHERE user_id>=20 and user_id<=30');

    while (
    $row=mysql_fetch_array($query))
    {
    print_r($row);
    }  
    // А теперь строки, у которых user_id находится в списке

    $query=mysql_query('SELECT * FROM '.$table.' WHERE user_id in (1,25,32,42,54)');

    while (
    $row=mysql_fetch_array($query))
    {
    print_r($row);
    }
    Почитайте http://www.mysql.ru/docs/man/SELECT.html и что именно делает функция mysql_fetch_array
     
    _________________________
  8. MuXaJIbI4

    MuXaJIbI4 Member

    Joined:
    20 Nov 2008
    Messages:
    66
    Likes Received:
    7
    Reputations:
    0
    а какие у тебя в этой таблице есть индексы ... может они просто не используются
     
  9. geezer.code

    geezer.code Elder - Старейшина

    Joined:
    22 Jan 2007
    Messages:
    552
    Likes Received:
    358
    Reputations:
    90
    Индексировать нужно те поля, по которым ведется поиск.
    зы может это уже не мускул лагает, а сама тачка(мало опёры, слабый проц, параллельно играешь СоD4)
     
    #9 geezer.code, 10 Apr 2009
    Last edited: 10 Apr 2009
  10. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    Индекс первичный... с auto_increment
    вы меня запутали.... получается все правильно сделано, только вся проблема в сервере и кол-ве строк?

    p.s. оперы на 1000мб, на кроне висят скрипты постоянно что то добавляющие в базу..
     
  11. Gifts

    Gifts Green member

    Joined:
    25 Apr 2008
    Messages:
    2,494
    Likes Received:
    807
    Reputations:
    614
    Если эти самые 30 записей получаются таким методом. То проблема не в количестве строк, а в реализации
    PHP:
    $q=mysql_fetch_array(mysql_query('SELECT * FROM '.$table.' WHERE user_id='.$g['user_id'].' LIMIT 1'));
     
    _________________________
    1 person likes this.
  12. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    Да.... Спасибо!
     
  13. Gar|k

    Gar|k Moderator

    Joined:
    20 Mar 2009
    Messages:
    1,166
    Likes Received:
    266
    Reputations:
    82
    эм ну скромно добавлю посоветую вернее... почитай внимательно документацию по SQL запросам очень много интересного.

    Ваще базы данных эт наука ) со своей теорией (в нете можно многое найти)

    ну а чисто полезные советы:
    если ты делаешь SELECT * FROM но используешь тока например поле user_id
    это очень плохой тон тк базе да и памяти срипта потребуется больше времени на обработку чем если бы ты сделал SELECT user_id FROM

    очень часто нужно узнать количество полей там или подсчитать ченить
    начинающие программисты делают так

    SELECT * FROM и потом смотрят mysql_num_rows или ваще цикл $cnt++ ))

    в MySQL есть такая интересная штука как count()

    PHP:
    function rows($che,$tab,$par='')
        {
        
    $w='';
        if(
    $par<>''){$w='where';}

        
    $sql=mysql_query("select count($che) as \"cnt\" from $tab $w $par");
        
    $row=mysql_fetch_array($sql,MYSQL_ASSOC);
        
    mysql_free_result($sql);
        
        return 
    $row['cnt'];
        } 
    заметь я указываю аргумент у mysql_fetch_array потомучто без него функция возращяет 2 массива один с именами другой с цифрами типа $row[0], $row[id] + mysql_free_result($sql) - освобождает память от уже ненужных данных

    есть еще интересная функция например max которая выберает максимальный элемент одним запросом... почитай в общем.

    Ну и не забывай о безопасности
    всегда значения передаваемые в WHERE пиши в кавычках типа WHERE id='1' это спасет тебя если на серверы включены magic_quotes_gpc типа id=1' OR 1=1/*

    ВСЕ входящиее переменные особено $_GET нужно проверять и явно указывать их тип (спасет от подстав типа ?page[]=2)

    например так

    $id=preg_replace("/\D/","",(int)$_GET['id']);

    Удаче, товарищь! )
     
    _________________________
    1 person likes this.
  14. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    Ооо... есть над чем думать.... ! +++++++ =)

    эм.. нагрузки не дадут 'лишние' ковычки?
     
  15. Gar|k

    Gar|k Moderator

    Joined:
    20 Mar 2009
    Messages:
    1,166
    Likes Received:
    266
    Reputations:
    82
    Лишних кавычек не бывает )))
    пример

    where id=$id / ?id=2-1 / id=2-1 (результ id=1)
    where id='$id' / ?id=2-1 / id='2-1' (результ ??? а результом будет id=2)


    PHP:
    <?php

    $sqlq
    =mysql_connect('localhost','root');
    mysql_select_db('test');

    function 
    sql($zap){
        echo 
    $zap."<br>";
    $sql=mysql_query($zap) or die(mysql_error()); 
        
    $row=mysql_fetch_array($sql,MYSQL_NUM); 


        echo 
    $row[0]." ".$row[2]."<br>";
        
    mysql_free_result($sql);
        }

    $id=$_GET['id'];

    sql("select * from gal where id=$id");
    sql("select * from gal where id='".$id."'");


    mysql_close($sqlq);

    ?>
    еще заметь die(mysql_error()) - так делать можно только на стадие дебага ... хакир ваще не должен знать че происходит
    даже отсутсвие каких либо выводимых данных признак того что ошибка есть, поэтому нужно обязон делать проверки типа

    if(mysql_num_rows() > 0)
    else { $id=1 ; }

    а лучше ваще перенаправления куданить на главную или к списку там тем незнаю чего ) меня лично это очень добивает потомучто приходится возвращатся на зад и тестить дальше ))))
     
    _________________________
    #15 Gar|k, 11 Apr 2009
    Last edited: 11 Apr 2009
  16. VDShark

    VDShark Elder - Старейшина

    Joined:
    1 Feb 2007
    Messages:
    260
    Likes Received:
    158
    Reputations:
    62
    Gar|k "Лишних кавычек не бывает )))"

    Лишние кавычки конечно же бывают, ибо тогда производится неявное преобразование типов, что на больших объемах данных может дать заметное замедление. Так что необходим смотреть на это дело со стороны безопасности - необходимы ли они в конкретном случае или нет.
     
  17. GreenBear

    GreenBear наркоман с медалью

    Joined:
    7 May 2005
    Messages:
    2,548
    Likes Received:
    1,397
    Reputations:
    612
    используй индексы! у меня из 200к рандомно 20 рядов берет за 0.02 секунд!
     
    1 person likes this.
  18. rcc0023

    rcc0023 Elder - Старейшина

    Joined:
    3 Jul 2008
    Messages:
    100
    Likes Received:
    6
    Reputations:
    0
    А как использовать (организовать, создать) индексы?
     
  19. Gar|k

    Gar|k Moderator

    Joined:
    20 Mar 2009
    Messages:
    1,166
    Likes Received:
    266
    Reputations:
    82
    Ну я понимаю это так

    таблица
    id text

    id=primary key, auto_increment (писал по памяти)

    ну и все select text from table where id=5

    хотя я могу ошибатся я пока теорию мало изучал может еше чам че замудреное есть )
     
    _________________________