MySQL의 여러 업데이트


388

한 번에 여러 행을 삽입 할 수 있다는 것을 알고 있습니다 .MySQL에서 한 번에 여러 행을 한 번에 업데이트하는 방법이 있습니까?

편집 : 예를 들어 다음이 있습니다.

Name   id  Col1  Col2
Row1   1    6     1
Row2   2    2     3
Row3   3    9     5
Row4   4    16    8

다음 업데이트를 모두 하나의 쿼리로 결합하고 싶습니다.

UPDATE table SET Col1 = 1 WHERE id = 1;
UPDATE table SET Col1 = 2 WHERE id = 2;
UPDATE table SET Col2 = 3 WHERE id = 3;
UPDATE table SET Col1 = 10 WHERE id = 4;
UPDATE table SET Col2 = 12 WHERE id = 4;

답변:


651

예, 가능합니다-중복 키 업데이트에 INSERT ... ON을 사용할 수 있습니다.

귀하의 예를 사용하여 :

INSERT INTO table (id,Col1,Col2) VALUES (1,1,1),(2,2,3),(3,9,3),(4,10,12)
ON DUPLICATE KEY UPDATE Col1=VALUES(Col1),Col2=VALUES(Col2);

22
중복이 없으면 해당 행을 삽입하고 싶지 않습니다. 무엇을해야합니까? ID가있는 테이블을 유지 관리하는 다른 사이트에서 정보를 가져 오기 때문입니다. 해당 ID와 관련하여 값을 삽입하고 있습니다. 사이트에 새로운 레코드가 있으면 ID 만 삽입하고 다른 모든 정보를 제외하고 계산합니다. ID에 대한 항목이있는 경우에만 업데이트해야하며 그렇지 않으면 건너 뛰어야합니다. 내가 무엇을하여야한다?
Jayapal Chandran

33
참고 :이 답변은 또한 ID가 기본 키입니다 가정
JM4

11
@JayapalChandran 당신은 ON DUPLICATE KEY UPDATE와 함께 INSERT IGNORE를 사용해야합니다. dev.mysql.com/doc/refman/5.5/en/insert.html
Haralan Dobrev에게

16
@HaralanDobrev INSERT IGNORE를 사용하면 여전히 복제되지 않은 레코드가 삽입됩니다. Jayapal은 피하고 싶었습니다. INSERT은 경고 :(에 오류가집니다 무시 stackoverflow.com/questions/548541/...
타케 히로 아다치

2
이 답변은 ID가 고유 키라고 가정하지만 (다른 사람들이 말했듯이 기본이 될 수 있음) 더 중요한 것은 다른 고유 키가 없다고 가정합니다. 있다면 스패너를 던질 수 있습니다.
Steve Horvath

129

동적 값이 있으므로 열을 업데이트하려면 IF 또는 CASE를 사용해야합니다. 좀 못 생겼지 만 작동해야합니다.

예제를 사용하면 다음과 같이 할 수 있습니다.

업데이트 테이블 SET Col1 = CASE id 
                          1시 1시 
                          2시 2시 
                          4시 10시 
                          ELSE Col1 
                        종료, 
                 Col2 = CASE ID 
                          3시 3시 
                          4시 12시 
                          ELSE Col2 
                        종료
             id IN (1, 2, 3, 4);

아마 그래서 꽤 동적 업데이트 만 케이스의 기능에 재미있는 모양으로 ...에 대한 쓰기에
me_

1
@ user2536953, 동적 업데이트에도 좋습니다. 예를 들어, PHP에서 해당 솔루션을 루프로 사용했습니다.$commandTxt = 'UPDATE operations SET chunk_finished = CASE id '; foreach ($blockOperationChecked as $operationID => $operationChecked) $commandTxt .= " WHEN $operationID THEN $operationChecked "; $commandTxt .= 'ELSE id END WHERE id IN ('.implode(', ', array_keys(blockOperationChecked )).');';
Boolean_Type

86

질문은 오래되었지만 다른 답변으로 주제를 확장하고 싶습니다.

내 요점은 그것을 달성하는 가장 쉬운 방법은 트랜잭션으로 여러 쿼리를 래핑하는 것입니다. 허용되는 대답 INSERT ... ON DUPLICATE KEY UPDATE은 좋은 해킹이지만 단점과 한계를 알고 있어야합니다.

  • 말했듯이, 기본 키가 테이블에 존재하지 않는 행으로 쿼리를 시작하면 쿼리는 새로운 "반 베이크"레코드를 삽입합니다. 아마 당신이 원하는 것이 아닐 것입니다
  • 기본값이없는 null이 아닌 필드가있는 테이블이 있고 쿼리 에서이 필드를 터치하지 않으려는 "Field 'fieldname' doesn't have a default value"경우 단일 행을 전혀 삽입하지 않아도 MySQL 경고가 표시됩니다. 엄격하고 mysql 경고를 앱에서 런타임 예외로 설정하면 문제가 발생할 수 있습니다.

제안 된 3 가지 변형에 대해 몇 가지 성능 테스트를 수행했습니다. INSERT ... ON DUPLICATE KEY UPDATE변형, "case / when / then"절이있는 변형 및 트랜잭션에 대한 순진한 접근을 수행했습니다. 당신은 파이썬 코드와 결과를 얻을 수 있습니다 여기에 . 전반적인 결론은 case 문이있는 변형이 다른 두 변형보다 두 배 빠르다는 것이지만 올바른 코드와 삽입 안전 코드를 작성하는 것은 매우 어렵 기 때문에 개인적으로 가장 간단한 접근법 인 트랜잭션 사용을 고수합니다.

편집 : Dakusan의 결과는 내 성능 평가가 상당히 유효하지 않다는 것을 증명합니다. 보다 정교한 다른 연구에 대해서는 이 답변 을 참조하십시오 .


트랜잭션을 사용하면 매우 훌륭하고 간단한 팁이 있습니다!
mTorres

내 테이블이 InnoDB 유형이 아닌 경우 어떻게합니까?
TomeeNS

1
누군가이 거래를하기 위해 어떤 거래에 대한 링크를 제공 할 수 있습니까? 그리고 / 또는 case 서술문을 가진 변형을위한 주입 안전 코드를위한 코드?
François M.

1
이 게시물에서 속도에 관한 정보를 잘못 찾았습니다. 나는 아래 게시물에 그것에 대해 썼습니다. stackoverflow.com/questions/3432/multiple-updates-in-mysql/…
Dakusan

1
@Dakusan, 좋은 대답입니다. 내 결과를 확장하고 주석을 달고 수정 해 주셔서 감사합니다.
로마 Imankulov

72

다른 유용한 옵션이 아직 언급되지 않은 이유는 확실하지 않습니다.

UPDATE my_table m
JOIN (
    SELECT 1 as id, 10 as _col1, 20 as _col2
    UNION ALL
    SELECT 2, 5, 10
    UNION ALL
    SELECT 3, 15, 30
) vals ON m.id = vals.id
SET col1 = _col1, col2 = _col2;

4
이게 최선이다. 특히 내가하고있는 것처럼 다른 SQL 쿼리에서 업데이트 값을 가져 오는 경우.
v010dya

1
이것은 대량의 열이있는 테이블을 업데이트 할 때 유용했습니다. 아마이 쿼리를 앞으로도 많이 사용할 것입니다. 감사!
캐스퍼 윌크스

이 유형의 쿼리를 시도했습니다. 그러나 레코드가 30k에 도달하면 경계 서버가 중지되었습니다. 다른 해결책이 있습니까?
Bhavin Chauhan

멋지다. 이것을 기본 키가 업데이트되지 않지만 변경할 열을 식별하는 데 사용되는 WHERE 절과 결합하려고 시도합니다.
nl-x

@BhavinChauhan 문제를 피하기 위해 join-select 대신 임시 테이블을 사용해 보셨습니까?
nl-x

41

다음은 모두 InnoDB에 적용됩니다.

세 가지 방법의 속도를 아는 것이 중요하다고 생각합니다.

3 가지 방법이 있습니다 :

  1. INSERT : ON DUPLICATE KEY UPDATE로 INSERT
  2. 거래 : 거래 내 각 레코드에 대한 업데이트를 수행하는 경우
  3. 사례 : UPDATE 내의 각기 다른 레코드에 대해 사례 / 시간

방금 이것을 테스트했으며 INSERT 방법은 6.7x 였습니다. TRANSACTION 방법보다 빠릅니다. 나는 3,000 행과 30,000 행을 시도했습니다.

TRANSACTION 메서드는 여전히 각 개별 쿼리를 실행해야하지만 실행하는 동안 결과를 메모리 등으로 일괄 처리하지만 시간이 걸립니다. TRANSACTION 방법은 복제 및 쿼리 로그 모두에서 상당히 비쌉니다.

더 나쁜 것은 CASE 방법이 30,000 레코드의 INSERT 방법보다 41.1 배 느리다는 것입니다 (TRANSACTION보다 6.1 배 느림). 그리고 MyISAM에서 75 배 더 느립니다. INSERT 및 CASE 방법은 ~ 1,000 레코드에서도 끊어졌습니다. 100 개의 레코드에서도 CASE 방법이 엄청나게 빠릅니다.

따라서 일반적으로 INSERT 방법이 가장 좋고 사용하기 쉽다고 생각합니다. 쿼리는 더 작고 읽기 쉬우 며 하나의 쿼리 작업 만 수행합니다. 이것은 InnoDB와 MyISAM 모두에 적용됩니다.

보너스 물건 :

INSERT 비 기본 필드 문제에 대한 해결책은 관련 SQL 모드를 일시적으로 해제하는 것 SET SESSION sql_mode=REPLACE(REPLACE(@@SESSION.sql_mode,"STRICT_TRANS_TABLES",""),"STRICT_ALL_TABLES","")입니다. sql_mode되돌릴 계획이라면 첫 번째 를 저장하십시오 .

다른 의견에 관해서는 auto_increment가 INSERT 메소드를 사용하여 올라간다는 것을 알았습니다 .InnoDB에서는 그렇지 않지만 MyISAM에서는 그렇지 않습니다.

테스트를 실행하는 코드는 다음과 같습니다. 또한 PHP 인터프리터 오버 헤드를 제거하기 위해 .SQL 파일을 출력합니다.

<?
//Variables
$NumRows=30000;

//These 2 functions need to be filled in
function InitSQL()
{

}
function RunSQLQuery($Q)
{

}

//Run the 3 tests
InitSQL();
for($i=0;$i<3;$i++)
    RunTest($i, $NumRows);

function RunTest($TestNum, $NumRows)
{
    $TheQueries=Array();
    $DoQuery=function($Query) use (&$TheQueries)
    {
        RunSQLQuery($Query);
        $TheQueries[]=$Query;
    };

    $TableName='Test';
    $DoQuery('DROP TABLE IF EXISTS '.$TableName);
    $DoQuery('CREATE TABLE '.$TableName.' (i1 int NOT NULL AUTO_INCREMENT, i2 int NOT NULL, primary key (i1)) ENGINE=InnoDB');
    $DoQuery('INSERT INTO '.$TableName.' (i2) VALUES ('.implode('), (', range(2, $NumRows+1)).')');

    if($TestNum==0)
    {
        $TestName='Transaction';
        $Start=microtime(true);
        $DoQuery('START TRANSACTION');
        for($i=1;$i<=$NumRows;$i++)
            $DoQuery('UPDATE '.$TableName.' SET i2='.(($i+5)*1000).' WHERE i1='.$i);
        $DoQuery('COMMIT');
    }

    if($TestNum==1)
    {
        $TestName='Insert';
        $Query=Array();
        for($i=1;$i<=$NumRows;$i++)
            $Query[]=sprintf("(%d,%d)", $i, (($i+5)*1000));
        $Start=microtime(true);
        $DoQuery('INSERT INTO '.$TableName.' VALUES '.implode(', ', $Query).' ON DUPLICATE KEY UPDATE i2=VALUES(i2)');
    }

    if($TestNum==2)
    {
        $TestName='Case';
        $Query=Array();
        for($i=1;$i<=$NumRows;$i++)
            $Query[]=sprintf('WHEN %d THEN %d', $i, (($i+5)*1000));
        $Start=microtime(true);
        $DoQuery("UPDATE $TableName SET i2=CASE i1\n".implode("\n", $Query)."\nEND\nWHERE i1 IN (".implode(',', range(1, $NumRows)).')');
    }

    print "$TestName: ".(microtime(true)-$Start)."<br>\n";

    file_put_contents("./$TestName.sql", implode(";\n", $TheQueries).';');
}

1
당신은 여기서 주님의 일을하고 있습니다.;) 대단히 감사합니다.
chili

MariaDB에서 40k 행을 사용하여 GoLang과 PHP 간의 성능을 테스트하면서 PHP에서 2 초, golang에서 6 초 이상을 얻었습니다 .... 글쎄, 항상 GoLang이 PHP보다 빠르게 실행될 것이라고 들었습니다 !!! 그래서, 나는 성능을 향상시키는 방법을 궁금해하기 시작합니다 ... INSERT ... 복제 키 업데이트 사용 ... Golang에서 0.74 초, PHP에서 0.86 초 !!!!
Diego Favero

1
내 코드의 요점은 타이밍 결과를 언어 또는 라이브러리의 코드가 아닌 SQL 문으로 엄격하게 제한하는 것입니다. GoLang과 PHP는 완전히 다른 것을 의미하는 완전히 분리 된 2 개의 언어입니다. PHP는 주로 제한적이고 수동적 인 가비지 수집이있는 단일 스레드에서 단일 실행 스크립팅 환경을위한 것입니다. GoLang은 주요 언어 기능 중 하나로 공격적인 가비지 수집 및 멀티 스레딩을 사용하여 장기 실행 컴파일 응용 프로그램을위한 것입니다. 언어 기능과 이유면에서 거의 다를 수 있습니다. [계속]
Dakusan

따라서 테스트를 실행할 때 속도 측정을 SQL 문에 대한 "쿼리"함수 호출로 엄격하게 제한하십시오. 쿼리 호출이 아닌 소스 코드의 다른 부분을 비교하고 최적화하는 것은 사과와 오렌지를 비교하는 것과 같습니다. 결과를 이것으로 제한하면 (문자열이 미리 컴파일되어 준비가 되었음) 결과는 매우 비슷해야합니다. 그 시점의 차이점은 언어의 SQL 라이브러리의 결함이며 반드시 언어 자체는 아닙니다. 내 의견으로는, INSERT ON DUPLICATE 솔루션은 항상 최선의 선택이 될 것입니다. [계속]
Dakusan

GoLang에 대한 귀하의 의견이 더 빠르다는 것은 이러한 언어와 디자인의 수많은 경고 또는 뉘앙스를 고려하지 않은 엄청나게 넓은 진술입니다. 자바는 통역 된 언어이지만, 15 년 전에는 특정 시나리오에서 C와 거의 일치하는 속도를 낼 수 있다는 사실을 알게되었습니다. 그리고 C는 컴파일 된 언어이며 어셈블러 외에 가장 낮은 수준의 시스템 언어입니다. 저는 GoLang이하는 일을 정말 좋아하며 가장 일반적인 시스템 중 하나가되고 최적화 된 것이 될 수있는 힘과 유동성을 가지고 있습니다. [계속]
Dakusan

9

임시 테이블을 사용하십시오.

// Reorder items
function update_items_tempdb(&$items)
{
    shuffle($items);
    $table_name = uniqid('tmp_test_');
    $sql = "CREATE TEMPORARY TABLE `$table_name` ("
        ."  `id` int(10) unsigned NOT NULL AUTO_INCREMENT"
        .", `position` int(10) unsigned NOT NULL"
        .", PRIMARY KEY (`id`)"
        .") ENGINE = MEMORY";
    query($sql);
    $i = 0;
    $sql = '';
    foreach ($items as &$item)
    {
        $item->position = $i++;
        $sql .= ($sql ? ', ' : '')."({$item->id}, {$item->position})";
    }
    if ($sql)
    {
        query("INSERT INTO `$table_name` (id, position) VALUES $sql");
        $sql = "UPDATE `test`, `$table_name` SET `test`.position = `$table_name`.position"
            ." WHERE `$table_name`.id = `test`.id";
        query($sql);
    }
    query("DROP TABLE `$table_name`");
}

8
UPDATE table1, table2 SET table1.col1='value', table2.col1='value' WHERE table1.col3='567' AND table2.col6='567'

이것은 나중에 작동합니다.

MySQL 매뉴얼 에는 여러 테이블에 대한 참조가 있습니다.


6

하나의 쿼리에서 여러 문장을 언급하지 않는가? 않습니까?

PHP에서는 multi_query mysqli 인스턴스의 메소드 합니다.

보내는 사람 PHP 매뉴얼

MySQL은 선택적으로 하나의 명령문 문자열에 여러 명령문을 허용합니다. 한 번에 여러 문을 보내면 클라이언트-서버 왕복이 줄어들지 만 특별한 처리가 필요합니다.

다음은 업데이트 30,000 raw의 다른 3 가지 방법과 비교 한 결과입니다. @Dakusan의 답변을 기반으로 한 코드를 여기 에서 찾을 수 있습니다.

거래 : 5.5194580554962
삽입 : 0.20669293403625
케이스 : 16.474853992462
멀티 : 0.0412278175354

보시다시피 여러 명령문 쿼리가 가장 높은 답변보다 효율적입니다.

다음과 같은 오류 메시지가 표시되는 경우 :

PHP Warning:  Error while sending SET_OPTION packet

max_allowed_packet내 컴퓨터에있는 mysql 구성 파일 을 증가시킨 /etc/mysql/my.cnf다음 mysqld를 다시 시작 해야 할 수도 있습니다 .


아래의 모든 비교는 INSERT 테스트와 비교되었습니다. 방금 동일한 조건에서 테스트를 실행했으며 트랜잭션이 없으면 300 행 에서 145 배 느 렸습니다. 3000 행에서 753x 느립니다. 나는 원래 3 만 줄로 시작했지만 나는 점심을 먹으러 돌아와서 여전히 가고 있었다. 개별 쿼리를 실행하고 개별적으로 데이터베이스를 플러시하는 것은 엄청나게 비싸므로 의미가 있습니다. 특히 복제의 경우. 트랜잭션을 설정하면 큰 차이가 있습니다. 3,000 행에서 1.5 배 이상, 30,000 행에서 2.34x 걸렸습니다 . [계속]
Dakusan

그러나 당신은 (트랜잭션으로) 빠르다는 것에 옳았습니다. 3,000 행과 30,000 행 모두에서 INSERT 메소드를 제외한 모든 것보다 빠릅니다. 특별한 MySQL API 호출로 일괄 처리 되더라도 30,000 개의 쿼리보다 1 개의 쿼리를 실행하면 더 나은 결과를 얻을 수있는 방법은 절대 없습니다. 300 행만 실행하면 CASE 방법과 거의 동일한 그래프 곡선을 따르는 다른 모든 방법보다 훨씬 빠릅니다 (놀랍게도). 이것이 더 빠르다는 것은 두 가지 방법으로 설명 할 수 있습니다. 삽입 방법은 본질적으로 인해 항상 "ON DUPLICATE KEY 2 행을 삽입하는 제 존재 [연속]
Dakusan

UPDATE "는"INSERT "와"UPDATE "를 모두 발생시킵니다. 다른 하나는 인덱스 조회로 인해 한 번에 한 행 씩만 편집하는 SQL 프로세서의 작업이 적다는 것입니다. 하지만 추가 시험은 고체 보이는 심지어 확실 복제가이 통화를 처리 할 방법을 실제로 아니에요 이것은 또한 UPDATE 호출을하고 만 작업 삽입 호출 항상 하나의 INSERT 쿼리와 함께 가장 빠른 것입니다 것입니다...가.
Dakusan

41 초가 걸리는 for 루프 내에서 오류를 수정하기 위해 테이블에서 한 번에 300 개의 업데이트를 수행했습니다. 동일한 UPDATE 쿼리를 하나로 만드는 $mysqli->multi_query($sql)데 "0"초가 걸렸습니다. 그러나 후속 쿼리가 실패하여 별도의 "프로그램"으로 만들었습니다.
Chris K

감사. 다중 쿼리를 사용하여 약 5k 개의 행을 업데이트 할 수있었습니다 (더 이상 테스트하지 않았습니다). 누군가 PDO 솔루션을 찾고 있다면 : stackoverflow.com/questions/6346674/…
Scofield

3

주입 명령을 방지하기 위해 MySQL의 '안전 메커니즘'을 비활성화하는 '다중 명령문'이라는 설정을 변경할 수 있습니다. 일반적으로 MySQL의 '화려한'구현에서 사용자가 효율적인 쿼리를 수행하지 못하게합니다.

여기 ( http://dev.mysql.com/doc/refman/5.1/en/mysql-set-server-option.html )는 설정의 C 구현에 대한 정보입니다.

PHP를 사용하는 경우 mysqli를 사용하여 여러 명령문을 수행 할 수 있습니다 (php는 잠시 동안 mysqli와 함께 제공 된 것 같습니다)

$con = new mysqli('localhost','user1','password','my_database');
$query = "Update MyTable SET col1='some value' WHERE id=1 LIMIT 1;";
$query .= "UPDATE MyTable SET col1='other value' WHERE id=2 LIMIT 1;";
//etc
$con->multi_query($query);
$con->close();

희망이 도움이됩니다.


4
이것은 쿼리를 개별적으로 보내는 것과 같습니다. 유일한 차이점은 하나의 네트워크 패킷으로 모두 전송하지만 UPDATE는 여전히 별도의 쿼리로 처리된다는 것입니다. 한 트랜잭션으로 랩핑하는 것이 좋습니다. 그러면 변경 사항이 한 번에 테이블에 커밋됩니다.
Marki555

3
한 번의 거래로 어떻게 포장합니까? 보여주세요.
TomeeNS

@TomeeNS mysqli::begin_transaction(..)쿼리를 보내기 전과 mysql::commit(..)후에 사용하십시오 . 또는 쿼리 자체에서 START TRANSACTION첫 번째 및 COMMIT마지막 명령문으로 사용하십시오.
Juha Palomäki

3

동일한 테이블의 별칭을 사용하여 삽입하려는 ID를 제공 할 수 있습니다 (행별 업데이트를 수행하는 경우).

UPDATE table1 tab1, table1 tab2 -- alias references the same table
SET 
col1 = 1
,col2 = 2
. . . 
WHERE 
tab1.id = tab2.id;

또한 다른 테이블에서도 업데이트 할 수 있음이 분명합니다. 이 경우 업데이트는 "SELECT"문으로 두 배가되어 지정한 테이블의 데이터를 제공합니다. 쿼리에 업데이트 값을 명시 적으로 명시하고 있으므로 두 번째 테이블에는 영향을 미치지 않습니다.


2

업데이트시 조인을 사용하는 것도 가능할 수 있습니다.

Update someTable Set someValue = 4 From someTable s Inner Join anotherTable a on s.id = a.id Where a.id = 4
-- Only updates someValue in someTable who has a foreign key on anotherTable with a value of 4.

편집 : 업데이트중인 값이 데이터베이스의 다른 곳에서 나오지 않으면 여러 업데이트 쿼리를 발행해야합니다.


1

그리고 지금 쉬운 방법

update speed m,
    (select 1 as id, 20 as speed union
     select 2 as id, 30 as speed union
     select 99 as id, 10 as speed
        ) t
set m.speed = t.speed where t.id=m.id

-1

사용하다

REPLACE INTO`table` VALUES (`id`,`col1`,`col2`) VALUES
(1,6,1),(2,2,3),(3,9,5),(4,16,8);

참고 :

  • id는 기본 고유 키 여야합니다
  • 외래 키를 사용하여 테이블을 참조하면 REPLACE가 삭제 후 삽입되므로 오류가 발생할 수 있습니다.

-3

다음은 한 테이블의 모든 행을 업데이트합니다.

Update Table Set
Column1 = 'New Value'

다음은 Column2의 값이 5보다 큰 모든 행을 업데이트합니다.

Update Table Set
Column1 = 'New Value'
Where
Column2 > 5

둘 이상의 테이블을 업데이트하는 Unkwntech 의 모든 예가 있습니다

UPDATE table1, table2 SET
table1.col1 = 'value',
table2.col1 = 'value'
WHERE
table1.col3 = '567'
AND table2.col6='567'

-3

예 .. INSERT ON DUPLICATE KEY UPDATE sql 문을 사용하여 가능합니다. 구문 : INSERT INTO table_name (a, b, c) VALUES (1,2,3), (4,5,6) 중복 키 업데이트시 a = VALUES (a), b = VALUES (b), c = VALUES (c)


-5
UPDATE tableName SET col1='000' WHERE id='3' OR id='5'

이것은 당신이 찾고있는 것을 달성해야합니다. 더 많은 ID를 추가하십시오. 나는 그것을 테스트했다.


-7
UPDATE `your_table` SET 

`something` = IF(`id`="1","new_value1",`something`), `smth2` = IF(`id`="1", "nv1",`smth2`),
`something` = IF(`id`="2","new_value2",`something`), `smth2` = IF(`id`="2", "nv2",`smth2`),
`something` = IF(`id`="4","new_value3",`something`), `smth2` = IF(`id`="4", "nv3",`smth2`),
`something` = IF(`id`="6","new_value4",`something`), `smth2` = IF(`id`="6", "nv4",`smth2`),
`something` = IF(`id`="3","new_value5",`something`), `smth2` = IF(`id`="3", "nv5",`smth2`),
`something` = IF(`id`="5","new_value6",`something`), `smth2` = IF(`id`="5", "nv6",`smth2`) 

// 방금 PHP로 빌드

$q = 'UPDATE `your_table` SET ';

foreach($data as $dat){

  $q .= '

       `something` = IF(`id`="'.$dat->id.'","'.$dat->value.'",`something`), 
       `smth2` = IF(`id`="'.$dat->id.'", "'.$dat->value2.'",`smth2`),';

}

$q = substr($q,0,-1);

따라서 하나의 쿼리로 구멍 테이블을 업데이트 할 수 있습니다


나는 downvote하지 않았다,하지만 난 반대가 필요하지 않을 때, 세트를 수행하는 것입니다 생각 (, 당신은 여전히 그 일을하는 당신은 설정하는 경우 somethingsomething)
v010dya
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.