2016-11-04 15 views
0

を複製することにより、失敗したI持つ複数の乱数を生成し、次のコードを使用してMySQLデータベースの同じを挿入したアプリケーション:挿入非重複PHP複数の値を単一のクエリに挿入したときには、

FIELDAは、主キーとFIELDBがあります12桁のランダムキーは、要件として一意でなければならず、DB内で一意に設定される。

$datafields = array('fielda', 'fieldb', 'created_on'); 

$data = array(value1a, value1b, 'now()',value2a, value2b, 'now()' ....valueNa, valueNb, 'now()'); 
N(変数$ N)が行の合計数で、テーブル内のすべての挿入のために万人であり、典型的には約100,000です

function placeholders($text, $count=0, $separator=","){ 
    $result = array(); 
    if($count > 0){ 
     for($x=0; $x<$count; $x++){ 
      $result[] = $text; 
     } 
    } 

    return implode($separator, $result); 
} 
$pdo->beginTransaction(); // also helps speed up your inserts. 
for($i=0;$i<$N;$i++){ 
    $question_marks[] = '(' . placeholders('?', 7) . ')'; 

} 

$sql = "INSERT INTO code (" . implode(",", $datafields) . ") VALUES " . implode(',', $question_marks); 
$stmt = $this->db->prepare($sql); 
try { 
    $stmt->execute($data); 
} catch (PDOException $e){ 
    echo $e->getMessage(); 
} 
$pdo->commit(); 

I上記に以下の質問がありました:

私の場合、一度に100000行近くを挿入しています。私が正しく理解し、クエリの1つの行がfieldbまたはfieldaの重複を持っている場合でも、私は実行した実験を形成するクエリ全体が失敗します。

1)この動作を変更して、少なくとも重複しない行を挿入し、重複が検出された行数とフィールド値を戻して、それらの行のみを再生成できるようにすることは可能ですか?私はそれがDBに存在するか、生成されたコードの新しいセットが存在する場合、生成するすべてのコードについてPHPでチェックするのを避けるためにこれを行いたいと思います。私はインスタンスごとに100000から100万行のどこにでも挿入しており、このDBはもっと大きくなるだろう。挿入前に重複した値を検索するために使用しているarray_flip、in_arrayなどの操作では、大きなdbのメモリが不足しているため、アプリケーションがクラッシュしてPHPが重複しないようにしたい。

2)上記が可能ならば、私はMySQlに正常に挿入されたすべての行を返して、ユーザーに出力できるようにします。

答えて

0

MySQLレベルで挿入が失敗することを確認する必要があります。そのためには、乱数を一意のインデックスにする必要があります。例:

CREATE TABLE code (
    -- [...] 
    UNIQUE INDEX fieldb_unique (fieldb) 
); 

これには、データの整合性を確保するという追加の利点があります。

これを取得すると、失敗した挿入がPDOExceptionを投げることがわかります。

Error: 1062 SQLSTATE: 23000 (ER_DUP_ENTRY)

Message: Duplicate entry '%s' for key %d

The message returned with this error uses the format string for ER_DUP_ENTRY_WITH_KEY_NAME.

list($sqlstate, $mysql_code, $message) = $stmt->errorInfo(); 
if ($mysql_code==1062) { 
} 
:追加堅牢性のために、あなたは MySQL error code1062であるかどうかを確認する必要があります
関連する問題