最後に挿入された行から値を取得する方法は? [複製]
-
04-07-2019 - |
質問
この質問にはすでに回答があります:
- JDBCで挿入IDを取得する方法 12答え
最後に挿入された行から値を取得する方法はありますか
PKが自動的に増加する行を挿入していますが、このPKを取得したいと思います。 PKのみがテーブル内で一意であることが保証されています。
JDBCおよびPostgreSQLでJavaを使用しています。
解決
PostgreSQLでは、RETURNINGキーワードを使用して実行できます。
INSERT INTO mytable( field_1, field_2,... )
VALUES ( value_1, value_2 ) RETURNING anyfield
「anyfield」の値を返します。 " anyfield"シーケンスであってもなくてもかまいません。
JDBCで使用するには、次の手順を実行します。
ResultSet rs = statement.executeQuery("INSERT ... RETURNING ID");
rs.next();
rs.getInt(1);
他のヒント
java.sql.StatementのAPIドキュメントを参照してください。 。
基本的に、 executeUpdate()
または executeQuery()
を呼び出すときは、 Statement.RETURN_GENERATED_KEYS
定数を使用します。その後、 getGeneratedKeys
を呼び出して、その実行によって作成されたすべての行の自動生成キーを取得できます。 (JDBCドライバーが提供すると仮定します。)
これに沿って何かが行われます:
Statement stmt = conn.createStatement();
stmt.execute(sql, Statement.RETURN_GENERATED_KEYS);
ResultSet keyset = stmt.getGeneratedKeys();
JDBC 3.0を使用している場合、PKを挿入するとすぐにPKの値を取得できます。
方法を説明する記事は次のとおりです。 https://www.ibm .com / developerworks / java / library / j-jdbcnew /
Statement stmt = conn.createStatement();
// Obtain the generated key that results from the query.
stmt.executeUpdate("INSERT INTO authors " +
"(first_name, last_name) " +
"VALUES ('George', 'Orwell')",
Statement.RETURN_GENERATED_KEYS);
ResultSet rs = stmt.getGeneratedKeys();
if ( rs.next() ) {
// Retrieve the auto generated key(s).
int key = rs.getInt(1);
}
PostgreSQL JDBCドライバーバージョン 8.4-701 以降、 PreparedStatement#getGeneratedKeys()
は最終的に完全に機能します。ここでほぼ1年、実稼働で使用しています。
"プレーンJDBC"キーを返すようにするには、 PreparedStatement
を次のように作成する必要があります。
statement = connection.prepareStatement(SQL, Statement.RETURN_GENERATED_KEYS);
現在のJDBCドライバーのバージョンはこちら(現時点ではまだダウンロード可能です) 8.4-701)。
postgresqlのシーケンスはトランザクションセーフです。
を使用できますcurrval(sequence)
currval
このシーケンスのnextvalによって最後に取得された値を返します 現在のセッションで。 (エラーは nextvalが一度もなかった場合に報告されます これでこのシーケンスを呼び出す セッション。)これは セッションローカル値を返す、それ 次の場合でも予測可能な答えを与える 他のセッションはnextvalを実行しています その間。
ここでの回答に基づいて、私はそれをどのように解決したのですか:
Connection conn = ConnectToDB(); //ConnectToDB establishes a connection to the database.
String sql = "INSERT INTO \"TableName\"" +
"(\"Column1\", \"Column2\",\"Column3\",\"Column4\")" +
"VALUES ('value1',value2, 'value3', 'value4') RETURNING
\"TableName\".\"TableId\"";
PreparedStatement prpState = conn.prepareStatement(sql);
ResultSet rs = prpState.executeQuery();
if(rs.next()){
System.out.println(rs.getInt(1));
}
Statement
を使用している場合は、次の項目に進みます
//MY_NUMBER is the column name in the database
String generatedColumns[] = {"MY_NUMBER"};
Statement stmt = conn.createStatement();
//String sql holds the insert query
stmt.executeUpdate(sql, generatedColumns);
ResultSet rs = stmt.getGeneratedKeys();
// The generated id
if(rs.next())
long key = rs.getLong(1);
PreparedStatement
を使用している場合は、次を参照してください
String generatedColumns[] = {"MY_NUMBER"};
PreparedStatement pstmt = conn.prepareStatement(sql,generatedColumns);
pstmt.setString(1, "qwerty");
pstmt.execute();
ResultSet rs = pstmt.getGeneratedKeys();
if(rs.next())
long key = rs.getLong(1);
ID列にpostgresでシーケンスを使用します:
INSERT mytable(myid) VALUES (nextval('MySequence'));
SELECT currval('MySequence');
currvalは、同じセッションのシーケンスの現在の値を返します。
(MS SQLでは、@@ identityまたはSCOPE_IDENTITY()を使用します)
PreparedStatement stmt = getConnection(PROJECTDB + 2)
.prepareStatement("INSERT INTO fonts (font_size) VALUES(?) RETURNING fonts.*");
stmt.setString(1, "986");
ResultSet res = stmt.executeQuery();
while (res.next()) {
System.out.println("Generated key: " + res.getLong(1));
System.out.println("Generated key: " + res.getInt(2));
System.out.println("Generated key: " + res.getInt(3));
}
stmt.close();
SELECT currval( 'MySequence')を使用しないでください-失敗した挿入で値が増加します。
注釈付きのMyBatis 3.0.4およびPostgresqlドライバー9.0-801.jdbc4の場合、マッパーでインターフェースメソッドを定義します
public interface ObjectiveMapper {
@Select("insert into objectives" +
" (code,title,description) values" +
" (#{code}, #{title}, #{description}) returning id")
int insert(Objective anObjective);
@Insertの代わりに@Selectが使用されることに注意してください。
例:
Connection conn = null; PreparedStatement sth = null; ResultSet rs =null; try { conn = delegate.getConnection(); sth = conn.prepareStatement(INSERT_SQL); sth.setString(1, pais.getNombre()); sth.executeUpdate(); rs=sth.getGeneratedKeys(); if(rs.next()){ Integer id = (Integer) rs.getInt(1); pais.setId(id); } }
with 、Statement.RETURN_GENERATED_KEYS);"
no found。
その単純なコードを使用します:
// Do your insert code
myDataBase.execSQL("INSERT INTO TABLE_NAME (FIELD_NAME1,FIELD_NAME2,...)VALUES (VALUE1,VALUE2,...)");
// Use the sqlite function "last_insert_rowid"
Cursor last_id_inserted = yourBD.rawQuery("SELECT last_insert_rowid()", null);
// Retrieve data from cursor.
last_id_inserted.moveToFirst(); // Don't forget that!
ultimo_id = last_id_inserted.getLong(0); // For Java, the result is returned on Long type (64)
トランザクションを使用している場合、挿入後に SELECT lastval()
を使用して、最後に生成されたIDを取得できます。