2012-08-15 2 views
1

다음 코드를 사용하여 여러 레코드를 테이블에 삽입하고 있습니다. 당신이 볼 수 있듯이 쿼리가 루프에 있습니다. 루프가 실행될 때마다 별도의 SQL 쿼리가 실행되어 삽입됩니다.PHP mysql에서 삽입 쿼리를 최적화해야합니다.

여러 쿼리를 실행하는 대신 단일 INSERT SQL 쿼리 만 여러 insert 문으로 실행해야하는 방식이 필요합니다.

비록이 코드가 완벽하게 작동하지만 최적화해야합니다.

$managed_ailments = unserialize($ailments); 
foreach($managed_ailments as $ailment_id) 
{ 
    $sql = "INSERT INTO ". TABLE_PATIENTS_AILMENTS_RECORDS .""; 
    $sql .= "(patient_id, ailment_id, datecreated) VALUES"; 
    $sql .= "($patient_id, $ailment_id, now())"; 
    $query = $mysql->query($sql); 
} 

여기에서 $ managed_ailments는 일련 화되지 않은 배열입니다. 배열에는 하나 이상의 값이있을 수 있습니다. $ mysql-> query ($ sql)은 내 사용자 지정 함수입니다.

이 코드를이 모든 코드를 단일 SQL 쿼리로 변환하는 데 도움을주십시오.

미리 감사드립니다. 이 같은

+0

에 대한 링크입니다 '. ""'4 줄의 끝에서? 빈 문자열을 추가하고 있습니다. – awm

+0

@awm 나는 의도가 공간이라고 생각하고 있습니다. – Kermit

+0

@njk 네 말이 맞는 것 같아. – awm

답변

3

뭔가 작업을해야합니다 :

$managed_ailments = unserialize($ailments); 
$sql = "INSERT INTO ". TABLE_PATIENTS_AILMENTS_RECORDS .""; 
$sql .= "(patient_id, ailment_id, datecreated) VALUES ("; 

$query_parts = array(); 

foreach($managed_ailments as $ailment_id) { 
    $query_parts[] = "($patient_id, $ailment_id, now()"; 
} 
$sql .= implode(",", $query_parts); 
$sql .= ")"; 

$query = $mysql->query($sql); 
+0

'$ ailments'가 충분히 커서'$ sql'이 목표 시스템의 최대 허용 패킷보다 큰 경우 어떻게됩니까? – TerryE

+0

@ 테리 당신이 네트워크 패킷을 의미하지 않는다면 나는 MySQL에서 그러한 최대 패킷 크기를 알지 못한다. 후자의 경우 그것은 중요하지 않습니다. MySQL에 대한 최대 쿼리 길이가있는 경우 쿼리를 중단하고 한 번에 X 레코드 만 삽입하는 방법을 찾아야합니다. – Telgin

+0

[Packet too large] (http://dev.mysql.com/doc/refman/5.1/en/packet-too-large.html)을 참조하십시오. 이것은 일반적으로 16MB입니다. 하지만 제약 조건과 약간의 시간이 걸릴 수도 있습니다. 그러면 코드가 자동으로 실패합니다. 여기에 또 다른 문제가 있습니다. 즉, 10K 행을 업데이트하는 경우, MyISAM이 긴 시간 동안 잠길 것이고 테이블을 원하는 다른 요청은 실속하게됩니다. – TerryE

1

당신은, 즉를 쿼리를 내리고 자 recordthen 각각에 대한 값 문을 추가 할 수 있습니다

INSERT INTO example 
    (example_id, name, value, other_value) 
VALUES 
    (100, 'Name 1', 'Value 1', 'Other 1'), 
    (101, 'Name 2', 'Value 2', 'Other 2'), 
    (102, 'Name 3', 'Value 3', 'Other 3'), 
    (103, 'Name 4', 'Value 4', 'Other 4'); 
1

당신은 문을 준비하고있다 MySQLi 확장을 사용할 수 있습니다. 템플릿을 한 번 서버로 보낸 다음 데이터를 전송하는 루프를 사용합니다.

//initialize and connect $mysqli via MySQLi extension 


$sql = "INSERT INTO ". TABLE_PATIENTS_AILMENTS_RECORDS .""; 
$sql .= "(patient_id, ailment_id, datecreated) VALUES"; 
$sql .= "(?, ?, now())"; 

$stmt = $mysqli->prepare($query) 

$managed_ailments = unserialize($ailments); 
foreach($managed_ailments as $ailment_id) { 
    $stmt->bind_param("ii", $patient_id, $ailment_id); 
    $stmt->execute(); 
} 

$ patient_id, $ ailment_id가 모두 정수라고 가정합니다. 또한 $ 쿼리를 겹쳐 쓰므로 실행 된 쿼리의 결과를 유지하지 않으려는 경우

이렇게하면 NOW() 함수의 오버 헤드가 줄고 대역폭이 절약됩니다. 여기

는의 목적은 무엇 PHP MySQLi Documentation

관련 문제