0

約 4 億行の正規化されていないデータベースがあります。すべての繰り返しデータを新しい正規化されたデータベースに移動したので、ID で表すことができます。

ここで、すべてのデータ エントリを移動し、ID を含むエントリに変換する必要があります。

問題は、400m の行では時間がかかることです..最適化の助けが必要です。

このクエリは 1 行あたり 0.4 秒かかるため、数か月かかります。

INSERT IGNORE INTO normalized.entry (insDate, `date`, project, keyword, url, position, competition, serachEngine)
SELECT 
CURDATE() as insDate
, d.id as dateId
, p.id as projectId
, k.id as keywordId
, z.id AS urlId 
, old.position
, old.competition
, s.id as searchEngineId

FROM unnormalized.bigtable old
INNER JOIN normalized.`date` d  ON old.insDate = d.`date`
INNER JOIN normalized.project p ON old.awrProject = p.project
INNER JOIN normalized.searchEngine s ON old.searchEngine = s.searchEngine
INNER JOIN normalized.keyword k ON old.keyword = k.keyword
INNER JOIN normalized.urlHash z ON old.url = z.url
WHERE old.id >= ".$start." AND old.id <= ".$stop."";

より多くの php を使用して 2 つのクエリに分割すると、この方法でエントリごとに 0.07 秒しかかかりませんが、それでも数か月かかります。

$q = "SELECT tmp.id
              , d.id as dateId
              , p.id as projectId
              , k.id as keywordId
              , tmp.position
              , tmp.competition
              , s.id as searchEngineId
              , tmp.url
              , z.id AS urlId 
               FROM unnormalized.bigtable tmp
        INNER JOIN normalized.`date` d ON tmp.insDate = d.`date`
        INNER JOIN normalized.project p ON tmp.awrProject = p.project
        INNER JOIN normalized.searchEngine s ON tmp.searchEngine = s.searchEngine
        INNER JOIN normalized.keyword k ON tmp.keyword = k.keyword
        INNER JOIN normalized.urlHash z ON tmp.url = z.url
        WHERE tmp.id > ".$start." AND tmp.id < ".$stop."";
        // echo $q;
            $result = mysql_query($q, $local);
            if (mysql_num_rows($result) > 0) {
            while ($row = mysql_fetch_array($result)) {
            $q = "SELECT id FROM normalized.url WHERE url = '".$row["url"]."'";
            $resultUrl = mysql_query($q, $local);
            $rowUrl = mysql_fetch_array($resultUrl);

            $q = "INSERT IGNORE normalized.entry (insDate, `date`, project, keyword, url, position, competition, serachEngine) VALUES (NOW(), '".$row["dateId"]."', '".$row["projectId"]."', '".$row["keywordId"]."', '".$rowUrl["id"]."', '".$row["position"]."', '".$row["competition"]."', '".$row["searchEngineId"]."')";

半年もかからずにこのデータを移植する方法がわからない! /必要なすべてのヘルプ

仕様: RDS amazon サーバーで InnoDB を使用しています。

編集: 最初のクエリの EXPLAIN SELECT:

id,select_type,table,type,possible_keys,key,key_len,ref,rows,Extra 1,SIMPLE,p,index,NULL,projectName,42,NULL,1346,"インデックスの使用" 1,SIMPLE,s,index,NULL ,searchEngine,42,NULL,2336,"インデックスの使用; 結合バッファーの使用" 1,SIMPLE,k,index,NULL,keyword,42,NULL,128567,"インデックスの使用; 結合バッファーの使用" 1,SIMPLE,tmp,ref ,"keyword_url_insDate,keyword,searchEngine,url,awrProject",keyword_url_insDate,767,func,115,"where の使用" 1,SIMPLE,d,eq_ref,date,date,3,intradb.tmp.insDate,1,"where の使用; インデックスの使用" 1,SIMPLE,z,ref,url,url,767,bbointradb.tmp.url,1,"インデックスの使用"

テーブルの作成を表示:

'rankingUrls201001', 'CREATE TABLE rankingUrls201001( idint(11) NOT NULL AUTO_INCREMENT, insDatedatetime NOT NULL, keywordvarchar(255) COLLATE utf8_swedish_ci NOT NULL, searchEnginevarchar(25) COLLATE utf8_swedish_ci NOT NULL, urlvarchar(255) COLLATE utf8_swedish_ci NOT(1 NULL, positionint(1 NULL) ) NOT NULL, competitionvarchar(20) COLLATE utf8_swedish_ci NOT NULL, awrProjectvarchar(200) COLLATE utf8_swedish_ci NOT NULL, servervarchar(20) COLLATE utf8_swedish_ci NOT NULL, rankvarchar(40) COLLATE utf8_swedish_ci NOT NULL, PRIMARY KEY ( id), KEY ) keyword_url_insDate( keyword, 、キー( )、キー( )、キー( )、キー(urlinsDatekeywordkeywordsearchEnginesearchEngineurlurlawrProjectawrProject) ) ENGINE=InnoDB AUTO_INCREMENT=2266575 DEFAULT CHARSET=utf8 COLLATE=utf8_swedish_ci'

4

1 に答える 1

0

@Robin、データ転送プロセスを高速化するには、適切な手順を実行して、すべての処理がメモリ内で行われるようにし、可能な限りディスクへの書き込みを避ける必要があります。次の手順を実行すると、ファイル転送の処理時間が短縮されます。

  1. 最初に、可能な限り多くの一時ワークスペースが割り当てられるように DB インスタンスを設定します。

  2. 次に、プロセスを複数ステップのプロセスに分割して、各処理フェーズが最小限のディスクへの書き込みアクティビティで完了するようにします。

  3. 最後に、バイナリ ログを無効にします。これにより、ディスクへの書き込み処理が削減され、多くの場合、クエリの応答時間が半分に短縮されます。

これらの手順によりプロセスが高速化されますが、データ行の量を考慮すると、転送と処理に一定の時間がかかる場合があります。

于 2012-11-06T15:38:07.463 に答える