0

日常的に情報を収集するデータベースを作りました。カレンダーと同様に、データベースにはメンバーの 1 日の金額が格納されます。月が既存の月 (MY) と一致しない場合、データベースは新しい html 月テーブルを作成します。次のように、この問題を解決しました。

mysql_query("something goes here");
while(condition)
{
    mysql_query("something goes here")
    while(condition)
    {
        mysql_query("something goes here");
        while()
        {
            ....................
        }
        ........................
    }
}

このアルゴリズムは、私が発見したときはうまく機能しました。しかし、数日後、サーバーに大きな負荷がかかりました。次に、PHP で同じアルゴリズムを試しました (しかし、これはできません)。これをより速く実行するにはどうすればよいですか? コードは次のとおりです。

        $q2=mysql_query("SELECT  a.member_id,a.dates,MONTH(dates) AS months,
                        YEAR(dates)AS years,sum(amount) as sums
                        FROM account AS a
                        left join member as m
                        on(a.member_id=m.member_id)
                        GROUP BY (SELECT EXTRACT(YEAR_MONTH FROM dates))
                        ORDER by dates DESC
        ");
        $k=0;
        while($data2=mysql_fetch_assoc($q2))
        {
            $months=$data2['months'];
            $years=$data2['years'];
            $daten = new DateTime($data2['dates']);

            print "<tr><th align='left'><b>".$daten->format('F-Y')."</b></th>";

            $q3=mysql_query("select * from member");

            while($data3=mysql_fetch_assoc($q3))
            {
                $id3=$data3['member_id'];
                $q4=mysql_query("
                                SELECT SUM(amount) AS total FROM account
                                WHERE member_id=$id3
                                AND month(dates)=$months
                                AND year(dates)=$years                              
                            ");
                while($data4=mysql_fetch_assoc($q4))
                {
                    $total=$data4['total'];

                    print "<td class='total'>".number_format($total)."</td>";
                }
            }
            print "<td class='total'><b>".$data2['sums']."</b></td></tr>";
            $k=$k+$data2['sums'];
        }
4

2 に答える 2

2

とりわけ:

  • SELECT * FROM member最初のクエリのすべての行に対してクエリを実行しています。このクエリはループから独立しているため、毎回再実行するのは無駄です。

  • クエリの結果ごとに、別のSELECT * FROM memberクエリを実行しています ( )。このクエリにはいくつかの問題があります。SELECT SUM(amount) AS total FROM account ...

    • まず、GROUP BYメンバーごとに 1 つのクエリを実行する必要がないように、このクエリを を使用して前のクエリに組み合わせることができます。何かのようなもの:

      SELECT member_id, SUM(amount) AS total FROM account WHERE ... GROUP BY member_id

    • 第二に、あなたは を使用していますMONTH(dates) = $months AND YEAR(dates) = $years。これは、サーバーがすべての行を検査することを強制するため、非効率的です。に適切なインデックスがあれば、それを の範囲dates(たとえば)に変換すると速度が向上します。dates BETWEEN '$year-$months-01' AND '$year-$months-31'dates

一般的に: ループ内のクエリは避けてください。ページの生成に含まれるクエリの数は、可能な限り常に少なく、ほぼ一定の数にする必要があります。データとともに成長するべきではありません。

于 2013-01-14T19:19:21.710 に答える
0

MySQLデータベースに適切なインデックスを設定しましたか?これにより、パフォーマンスに大きな違いが生じる可能性があります。http://dev.mysql.com/doc/refman/5.0/en/mysql-indexes.html

于 2013-01-14T19:07:24.720 に答える