あるテーブルからバッチデータをクエリし、それを別のテーブルに挿入する MySQL の完全な例

あるテーブルからバッチデータをクエリし、それを別のテーブルに挿入する MySQL の完全な例

事前に言っておく

Nodejs はデータベースを非同期操作として読み取るため、データベースがデータを読み取る前にコードの実行が継続されます。
最近何かを書いていたとき、データベースに対してバッチ データをクエリし、それを別のテーブルに挿入する必要がありました。
バッチ操作に関しては、 for ループが最も簡単に考えられます。

for ループのバージョンが間違っています

まずコードをリリースし、事前に説明します。ここでは、SQL 操作のカプセル化を示します: sql.sever (データベース接続プール、SQL ステートメント結合関数、コールバック関数)

for(let i=0;i<views.xuehao.length;i++){
	sql.sever(pool,sql.select(["name"],"registryinformation",["xuehao="+sql.escape(views.xuehao[i])]),function(data){
  sql.sever(pool,sql.insert("personnelqueue",["xuehao","name","selfgroup","time"],[sql.escape(views.xuehao[i]),data[0].name,selfgroup,'NOW()'],true),function(){
  let allGroup = ['Android', 'ios', 'Web', 'Backend', 'Product']; //ここにメール関連のコードがあります let group = allGroup[selfgroup - 1];
  let mailmsg = "こんにちは、" + group + "グループ承認リストが送信されました。できるだけ早く確認してください!";
  mail.mailepass(mailmsg);
  res.write(JSON.stringify({
   スタイル:1,
   メッセージ:「リストは送信されており、管理者による確認を待っています。」
  }));
  res.end();
  })
 })
}

上記のコードでは、最初にデータ クエリが実行され、次にデータ挿入が実行されます (ここでは、データが 2 つあると想定しています)。常識的に考えると、必要な実行順序は、クエリ挿入、クエリ挿入です。しかし、それは私たちが考えるほど単純ではありません。挿入操作は確かにデータベース クエリのコールバックに記述されていますが、実際の順序はクエリ クエリです。2 つのクエリが直接実行されると、後続のコードでエラーが報告されます。コールバックが実行される前に、2 番目のループがすでに実行されています。

改良された for ループ バージョン

mysql は、クエリと挿入を 1 つのステートメントで完了できます。形式は、INSERT IGNORE INTO insert table テーブル名 (item1、item2) SELECT item1、item2 FROM query table テーブル名 WHERE です。そこで、次の解決策を考えました。

(i = 0 とします; i < views.xuehao.length; i++) {
 sql.sever(pool, 'INSERT IGNORE INTO personnelqueue (xuehao,name,selfgroup,time) SELECT xuehao,name,selfgroup,NOW() FROM registryinformation WHERE xuehao=' + sql.escape(views.xuehao[i]) + ' and pass=' + state, function () {
  if (i == views.xuehao.length - 1) {
   allGroup を ['Android', 'ios', 'Web', 'Backend', 'Product'] とします。
   グループをallGroup[自己グループ - 1]とします。
   let mailmsg = "こんにちは、" + group + "グループ承認リストが送信されました。できるだけ早く確認してください!";
   mail.mailepass(mailmsg);
   res.write(JSON.stringify({
    スタイル: 1,
    メッセージ: 「リストは送信されており、管理者による確認を待っています。」
   }));
   res.end();
  }
 })
} 

このようにして、データベースは正しく動作し、目的が達成されます。しかし、よく考えてみると、このアプローチにはまだ欠陥があります。データ量が少ない場合は問題ありませんが、データ量が多い場合は、プログラムがデータベースと複数の接続を確立することになり、サーバーの負荷が増加します。

改良版

前回の欠陥と合わせて、名前が示すように、今回はプログラムがデータベースに接続する回数を減らす必要があります。したがって、挿入とクエリを一緒に記述するのではなく、それらを分離してバッチ挿入とクエリを実行し、クエリされたデータをバッチ挿入に使用します。コードは次のとおりです。

let sqlString = 'SELECT xuehao,name,selfgroup FROM registryinformation WHERE pass=' + state + ' AND (xuehao=' + sql.escape(views.xuehao[0]);
(i = 1 とします; i < views.xuehao.length; i++) {
 sqlString += ' または xuehao=' + sql.escape(views.xuehao[i]);
}
sqlString = sqlString + ')';
sql.sever(プール、sqlString、関数(データ) {
 //SQL ステートメントの結合と挿入 let istSqlStr = 'INSERT IGNORE INTO personnelqueue (xuehao,name,selfgroup,time) VALUES (' + data[0].xuehao + ',' + sql.escape(data[0].name) + ',' + data[0].selfgroup + ',NOW())';
 (j = 1; j < data.length; j++) の場合 {
 istSqlStr += ',(' + data[j].xuehao + ',' + sql.escape(data[j].name) + ',' + data[j].selfgroup + ',' + 'NOW())';
 }
 sql.sever(プール、istSqlStr、関数() {
 allGroup を ['Android', 'ios', 'Web', 'Backend', 'Product'] とします。
 グループをallGroup[自己グループ - 1]とします。
 let mailmsg = "こんにちは、" + group + "グループ承認リストが送信されました。できるだけ早く確認してください!";
 mail.mailepass(mailmsg);
 res.write(JSON.stringify({
  スタイル: 1,
  メッセージ: 「リストは送信されており、管理者による確認を待っています。」
 }));
 res.end();
 })
})

補充する

バッチ クエリ構文 (and と or が混在) SELECT column name, column name FROM table name WHERE condition AND (item1='xxx' OR item1='yyy');
バッチ挿入構文の 1 つのステートメント INSERT INTO [テーブル名]([列名],[列名]) VALUES([列値],[列値])),([列値],[列値])),([列値],[列値]));

要約する

これで、MySQL で 1 つのテーブルから大量のデータをクエリし、それを別のテーブルに挿入する方法についての説明は終わりです。MySQL クエリで大量のデータを別のテーブルに挿入する関連コンテンツについては、123WORDPRESS.COM の以前の記事を検索するか、次の関連記事を引き続き参照してください。今後とも 123WORDPRESS.COM をよろしくお願いいたします。

以下もご興味があるかもしれません:
  • データの挿入とクエリのためのMySQLコマンドとステートメントの詳細な説明
  • JDBC は MySql データベースのステップに接続し、クエリ、挿入、削除、更新などを実行します。
  • MySQL データの挿入とデータのクエリ

<<:  Dockerコンテナの接続と通信の実装

>>:  HTML テーブルタグチュートリアル (26): セルタグ

推薦する

Dockerを使用してgitlabコミュニティの中国語版を構築する詳細なプロセスを教えます

1. Docker Composeを使用して起動を構成するDocker Compose を知らない場...

互換性を維持しながら他のウェブページのデータを適用する iframe の使い方

以下は、Shiji Tiancheng が Tencent KartRider ページを呼び出すため...

Docker を使用して開発環境を構築する方法 (Windows および Mac)

目次1. Dockerを使用する利点2. Dockerをインストールする1) LinuxにDocke...

docker を使って sonarqube を構築する方法

目次1. Dockerをインストールする2. ソナーイメージをインストールする3. ソナーを使ってコ...

Centos7.4 サーバーへの Apache のインストールとインストール プロセス中に発生した問題の解決策

この記事では、CentOS 7.4 サーバーに Apache をインストールする方法と、インストール...

Webフロントエンドの一般的な操作(JS/HTML/CSSなどの知識を含む)

ul liの前のアイコン1をキャンセルしますクリア値1値を1に設定ラベル中央値1をクリアラベルの中央...

Dockerイメージが消える問題を解決する

1. 50と93では鏡像が消える [root@h50 /]# df -h ファイルシステムの使用済み...

Vue プロジェクトの最初の画面のパフォーマンス最適化コンポーネントの実践ガイド

目次Vue ファースト スクリーン パフォーマンス最適化コンポーネント説明するインターセクションオブ...

jQueryはネストされたタブ機能を実装します

この記事では、ネストされたタブ機能を実装するためのjQueryの具体的なコードを参考までに紹介します...

Dockerコンテナのネットワークポート設定プロセスの詳細な説明

ネットワークポートの公開実際、Docker にはネットワーク ポートの公開に関わる 2 つのパラメー...

JavaScript WebAPI、DOM、イベント、操作要素例の詳しい説明

目次ウェブAPI DOM DOMツリーDOM要素取得方法ドキュメントオブジェクトのプロパティイベント...

HTML でフロートをクリアする 2 つの方法

1. クリアフローティング法1前の親要素の高さを設定します。注: エンタープライズ開発では、可能であ...

MySQL 5.7.21 winx64 のインストールと設定方法のグラフィックチュートリアル

この記事では、MySQL 5.7.21のインストールに関する注意事項をまとめ、皆さんと共有します。 ...

H5でクリックされたときにaタグの背景色をキャンセルする方法

1. モバイル端末でクリックされたときにタグの青色を解除する { -webkit-tap-highl...

case when文のエラー問題の詳細な説明

序文MySQL データベースでは、if else のような判断演算を使用することがあります。では、M...