質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.51%
SQLite

SQLiteはリレーショナルデータベース管理システムの1つで、サーバーではなくライブラリとして使用されている。

Q&A

解決済

1回答

6038閲覧

異なるDB間で、特定のカラムのみコピーしたい

teshiya

総合スコア8

SQLite

SQLiteはリレーショナルデータベース管理システムの1つで、サーバーではなくライブラリとして使用されている。

0グッド

1クリップ

投稿2017/10/25 02:29

###前提・実現したいこと
自作のAndroidアプリ内でsqliteを利用しています。

構造が同じ2つのデータベースA,Bがあり、複数テーブルが存在します。
実現したいことは、データベースAのテーブル(tableA)の特定カラムのみを、データベースBのテーブル(tableB)の特定カラムにコピーしたいのです。
イメージとしては以下のような感じです。

■データベースA
tableA
id | Name | Num
1 | hoge1 | 0
2 | hoge2 | 0
3 | hoge3 | 0
4 | hoge4 | 0
5 | hoge5 | 0

tableB
id | Name | Num
1 | hoge1 | 5
2 | hoge2 | 4
3 | hoge3 | 3

tableAのidカラムとNameカラムのみをtableBへコピーしたい

■実現後のテーブル
tableB
id | Name | Num
1 | hoge1 | 5
2 | hoge2 | 4
3 | hoge3 | 3
4 | hoge4 | 0
5 | hoge5 | 0

idカラムとNameカラムは上書きコピー、Numだけは元のデータそのままにしたいイメージです。

###発生している問題・エラーメッセージ

異なるデータベース間なので、atttach database を利用しています。
テーブルそのもののコピーはできましたが、上記のように一部のカラムのみのコピー方法がわからず悩んでいます。

恐らくSQL文をうまく使えば実現できると思うのですが、当方初心者でよく理解できていないのが現状です。
上記を実現できるようなSQL文をご教示いただける方いらしたらお力添えいただければ幸いです。

###補足情報(言語/FW/ツール等のバージョンなど)
より詳細な情報

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

上記を実現できるようなSQL文をご教示いただける方いらしたらお力添えいただければ幸いです。

SQLとしてはUPDATEで上書き後、INSERTで足りない行を追加する、とのように2段階になるかなと思います。

最初のUPDATEで、idをキーにtableAのname をtableBのnameへセット。

SQL

1UPDATE tableB SET name 2 = (SELECT name FROM tableA WHERE id = tableB.id)

次に、tableAのidの内、tableBのidに無いものを抽出して、INSERT
。

SQL

1INSERT INTO tableB (id, name, num)SELECT id, name, 0 FROM tableA 2WHERE id NOT IN (SELECT id FROM tableB);

tableAは attach するので、tableBしか無いDB上で作業していてもtableAとしてそのまま使えることになります。attachさえすれば、上記のSQLをそのまま実行できるはずです。

せっかくですので、確認の為に使用したコード例を示します。

Java

1 private void example() { 2 SQLiteDatabase db = null; 3 try { 4 String sql; 5 // mHelper はSQLiteOpenHelperを継承したもの 6 db = mHelper.getWritableDatabase(); 7 8 // tableAがあるデータベースファイルをattach 9 String dbaPath = this.getDatabasePath("a.db").getPath(); 10 db.execSQL("attach database ? as tableA", new String[]{dbaPath}); 11 12 db.beginTransaction(); 13 sql = "UPDATE tableB SET name = (SELECT name FROM tableA WHERE id = tableB.id)" 14 ; 15 db.execSQL(sql); 16 17 sql = "INSERT INTO tableB (id, name, num)" 18 + "SELECT id, name, 0 FROM tableA WHERE id NOT IN (SELECT id FROM tableB)" 19 ; 20 db.execSQL(sql); 21 db.setTransactionSuccessful(); 22 } catch (Exception ex) { 23 Log.w(TAG, "Exception: " + ex.getMessage()); 24 } finally { 25 if (db != null) { 26 db.endTransaction(); 27 } 28 } 29 }

上記のコードでtableAとtableBを処理した例を示します。
(sqlite3のコマンドラインツールを使用しています)

# 初期状態のtableA (id, name, num) sqlite> select * from tableA; 1|hogeA1|11 2|hogeA2|12 3|hogeA3|13 4|hogeA4|14 5|hogeA5|15 # 初期状態のtableB (id, name, num) sqlite> select * from tableB; 1|hogeB1|5 2|hogeB2|4 3|hogeB3|3 # 処理後 (name はtableAのもので上書き) sqlite> select * from tableB; 1|hogeA1|5 2|hogeA2|4 3|hogeA3|3 4|hogeA4|0 5|hogeA5|0

余計なアドバイスかとも思いますが、SQLに慣れていない時は、sqlite3のコマンドラインツールやその他のSQLite3対応のツールを使って試し、SQL文自体の検証をすることをおすすめします。それでSQLが完成した後、Android用のプログラムへ落とし込むのが時間もかからず、近道になることが多いです。

投稿2017/10/27 13:01

dodox86

総合スコア9181

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

teshiya

2017/10/31 02:07

お返事遅くなり申し訳ありません。 ご丁寧にありがとうございました。 ご教示いただいた方法でイメージどおりの処理ができました!大変助かりました、ありがとうございます。
dodox86

2017/10/31 02:16

結果のご報告どうもありがとうございます。お役に立ててよかったです。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.51%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問