Maison >développement back-end >tutoriel php >Méthode Thinkphp pour mettre à jour les données par lots
Cet article présente principalement les informations pertinentes compilées par Thinkphp sur la méthode de mise à jour par lots des données. Il est très bon et a une valeur de référence. Les amis dans le besoin peuvent s'y référer
L'éditeur suivant a répertorié trois types. pour vous. La méthode d'implémentation des données de mise à jour par lots de thinkphp, pardonnez-moi si elle n'est pas bien écrite. Si vous avez des opinions, n'hésitez pas à les émettre, apprenons et progressons ensemble !
Méthode 1 :
//批量修改 data二维数组 field关键字段 参考ci 批量修改函数 传参方式 function batch_update($table_name='',$data=array(),$field=''){ if(!$table_name||!$data||!$field){ return false; }else{ $sql='UPDATE '.$table_name; } $con=array(); $con_sql=array(); $fields=array(); foreach ($data as $key => $value) { $x=0; foreach ($value as $k => $v) { if($k!=$field&&!$con[$x]&&$x==0){ $con[$x]=" set {$k} = (CASE {$field} "; }elseif($k!=$field&&!$con[$x]&&$x>0){ $con[$x]=" {$k} = (CASE {$field} "; } if($k!=$field){ $temp=$value[$field]; $con_sql[$x].= " WHEN '{$temp}' THEN '{$v}' "; $x++; } } $temp=$value[$field]; if(!in_array($temp,$fields)){ $fields[]=$temp; } } $num=count($con)-1; foreach ($con as $key => $value) { foreach ($con_sql as $k => $v) { if($k==$key&&$key<$num){ $sql.=$value.$v.' end),'; }elseif($k==$key&&$key==$num){ $sql.=$value.$v.' end)'; } } } $str=implode(',',$fields); $sql.=" where {$field} in({$str})"; $res=M($table_name)->execute($sql); return $res; } //测试 function test(){ $update_array=array(); for ($i=2; $i <7 ; $i++) { $data=array(); $data['id']=$i; $data['memeber_type']=2; $data['memeber_type_state']=1; $update_array[]=$data; } $res=$this->batch_update('yl_member',$update_array,id); var_dump($res); }
Méthode 2 :
consiste à parcourir les enregistrements de mise à jour un par un. Un enregistrement est mis à jour une seule fois, ce qui présente des performances médiocres et peut facilement provoquer un blocage.
Les mises à jour par lots peuvent-elles donc être implémentées avec une seule instruction SQL ? MySQL ne fournit pas de méthode directe pour implémenter les mises à jour par lots, mais cela peut être réalisé grâce à quelques astuces.
UPDATE categories SET display_order = CASE id WHEN 1 THEN 3 WHEN 2 THEN 4 WHEN 3 THEN 5 END WHERE id IN (1,2,3)
La signification de ce sql est de mettre à jour le champ display_order Si id=1, alors la valeur de display_order est 3. Si id=2. , alors la valeur de display_order est La valeur est 4. Si id=3, la valeur de display_order est 5.
signifie écrire des instructions conditionnelles ensemble.
La partie où ici n'affecte pas l'exécution du code, mais elle améliorera l'efficacité de l'exécution de SQL. Assurez-vous que l'instruction SQL n'exécute que le nombre de lignes qui doivent être modifiées ici. Seules 3 lignes de données sont mises à jour ici et la clause Where garantit que seules 3 lignes de données sont exécutées.
Si vous mettez à jour plusieurs valeurs, il vous suffit de les modifier légèrement :
UPDATE categories SET display_order = CASE id WHEN 1 THEN 3 WHEN 2 THEN 4 WHEN 3 THEN 5 END, title = CASE id WHEN 1 THEN 'New Title 1' WHEN 2 THEN 'New Title 2' WHEN 3 THEN 'New Title 3' END WHERE id IN (1,2,3)
Application pratique
$display_order = array( 1 => 4, 2 => 1, 3 => 2, 4 => 3, 5 => 9, 6 => 5, 7 => 8, 8 => 9 ); $ids = implode(',', array_keys($display_order)); $sql = "UPDATE categories SET display_order = CASE id "; foreach ($display_order as $id => $ordinal) { $sql .= sprintf("WHEN %d THEN %d ", $id, $ordinal); } $sql .= "END WHERE id IN ($ids)"; echo $sql;
La méthode 2 n'est pas recommandée.
Troisième méthode :
/* * @param $saveWhere :想要更新主键ID数组 * @param $saveData :想要更新的ID数组所对应的数据 * @param $tableName : 想要更新的表明 * @param $saveWhere : 返回更新成功后的主键ID数组 * */ public function saveAll($saveWhere,&$saveData,$tableName){ if($saveWhere==null||$tableName==null) return false; //获取更新的主键id名称 $key = array_keys($saveWhere)[0]; //获取更新列表的长度 $len = count($saveWhere[$key]); $flag=true; $model = isset($model)?$model:M($tableName); //开启事务处理机制 $model->startTrans(); //记录更新失败ID $error=[]; for($i=0;$i<$len;$i++){ //预处理sql语句 $isRight=$model->where($key.'='.$saveWhere[$key][$i])->save($saveData[$i]); if($isRight==0){ //将更新失败的记录下来 $error[]=$i; $flag=false; } //$flag=$flag&&$isRight; } if($flag ){ //如果都成立就提交 $model->commit(); return $saveWhere; }elseif(count($error)>0&count($error)<$len){ //先将原先的预处理进行回滚 $model->rollback(); for($i=0;$i<count($error);$i++){ //删除更新失败的ID和Data unset($saveWhere[$key][$error[$i]]); unset($saveData[$error[$i]]); } //重新将数组下标进行排序 $saveWhere[$key]=array_merge($saveWhere[$key]); $saveData=array_merge($saveData); //进行第二次递归更新 $this->saveAll($saveWhere,$saveData,$tableName); return $saveWhere; } else{ //如果都更新就回滚 $model->rollback(); return false; } }
Appel de la méthode de test :
public function test(){ //要更新的数据表的主键数组 $where['ID']=array(70,73,74,80,83); //ID主键数组对应的待更新数据 $save=array( array('School'=>'DK Univisity01','isExport'=>0), array('School'=>'DK Univisity02','isExport'=>0), array('School'=>'DK Univisity03','isExport'=>0), array('School'=>'DK Univisity04','isExport'=>0), array('School'=>'','isExport'=>0), // array('School'=>' Univisity05','isExport'=>0), ); $f=$this->saveAll($where,$save,'want'); if(count($f['ID'])>0){ //返回更新成功的ID数组 echo "This is success :</br>"; dump($f); echo 'ok'; }else{ //更新失败操作 echo "This is failed :</br>"; dump($f); echo 'error'; } }
Recommandations associées :
Comment implémenter un forum de discussion basé sur le framework thinkPHP
ThinkPHP implémente la fonction de téléchargement de pièces jointes
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!