2012-11-13 12 views
8

Oracleデータベースにデータを挿入する小さなプログラムを開発する必要があります。残念ながら、私はSQL Statementとそれの実行にいくつかの問題があります。これは私が使用していますコードです:Oracleデータベースにdouble値を挿入しようとするとSQLExceptionが発生する

db.execute(
    String.format("INSERT INTO tops VALUES (%d, '%s', %d, %f.00, '%s', TO_TIMESTAMP('%s', 'YYYY-MM-DD HH24:MI:SS.FF'))", 
     item.getID(), 
     item.getTitle(), 
     this.elements, 
     item.getSize(), 
     item.getEntity(), 
     timestamp.toString())); 

これは実行が動作するはず一部ですが、私は次のエラーを取得:例外のために

java.sql.SQLException: ORA-00913: Zu viele Werte 

Google Translateをされています

java.sql.SQLException: ORA-00913: Too many values 
+0

文字列の値から引用符を外すことができると思います。 –

+3

挿入したい値のような音がテーブルのスキーマと一致しません。 (あまりにも多くの値) – MicSim

+11

準備文を使用すると、文字列操作は本当に悪い考えです – Guillaume

答えて

5

のいずれかだったあなたは、このような準備された文を使用することができますコメントのGuallaume;

PreparedStatement pstmt = null; 
Connection conn = null; 

try{ 
    //if you have a method that creates a connection for you. 
    conn = getConnection(); 
    pstmt = conn.prepareStatement("INSERT INTO tops(id, title, elements, size, entity, timeStamp) VALUES(?,?,?,?,?,?)"); 
    pstmt.setInt(1,item.getID()); 

    //Assuming that title is a String data type 
    pstmt.setString(2,item.getTitle()); 
    pstmt.setString(3,this.elements); 
    pstmt.setDouble(4,item.getSize()); // <--- JDBC will make sure this works 

    //assuming Entity data type is String 
    pstmt.setString(5,item.getEntity()); 

    //if your timestamp's string format is 
    //well formed, you may insert as a string. 
    pstmt.setString(6,timestamp.toString()); 
    pstmt.executeUpdate(); 
}catch(Exception e){ 
    e.printStackTrace(); 
}finally{ 
    try{ 
     pstmt.close(); 
    }catch(Exception e){} 

    try{ 
     conn.close(); 
    }catch(Exception e){} 
} 
+0

私はformatingが少し良いことを望む。ご覧のとおり、プリペアドステートメントクエリに値を挿入する予定の列名を知っておく必要があります。例えば、 'INSERT INTO tops(id、title、elements、size、entity、timeStamp)VALUES(?、?、?、?、?)' 'ここでは、id、title、elemets、size、 'pstmt.setInt(1、item.getID());'は、最初の値を設定します。この値は、 'pstmt.setString(2、item.getTitle());'は2番目の値を設定し、 'pstmt.setString(3、this.elements);'は3番目の値を設定します... – mwangi

+0

ありがとうございます。 –

+0

ようこそパトリック:) – mwangi

3

この構文を使用しないでください。

​​

利用代わり

INSERT INTO table (col1, col2, ...) VALUES (val1, val2, ...) 

テーブルが変更されることがあり、この1。フィールドが追加/削除/並べ替えられることがあります。その場合、INSERTステートメントが再び中断されます。もちろん

、他の人が提案として、あなたが想像して... SQLインジェクションや構文エラーを回避するために準備されたステートメントを使用する必要があり、により示唆されるようにitem.getTitle()はこれら

"a', 'b"; 
"a'); DROP TABLE tops;' ..."; 
1

あなたは本当に私たちを信じて、PreparedStatementsのを使用する必要があります...この場合

は、しかし、問題はロケールが小数点のためにカンマ(,)文字を使用していることを、非常に可能性があります。..

したがって、1/4は:0,25で、0.25はDBのようになりません!

なぜこれが問題ですか?この時

ルック:

INSERT INTO SOMETABLE VALUES (0,25); 
INSERT INTO SOMETABLE VALUES (0, 25); 

両方が値を持つものとして扱われ、ちょうど最初のものは、あなたがする必要があるので...小数点としてコンマを使用し、私たちのために明らかにされていませんカンマをドットに変更するか、ロケールをUSに変更します。正しい

INSERT INTO SOMETABLE VALUES (0.25); 

あなたが適切なロケールを供給することによってString.format(Locale l, String format, Object... args)を使用して書式設定文字列のロケールを指定することができます。

+0

+1:いい考えです!それは可能性が高いです... –

+0

@LukasEder私は天才ではありません - 私は対処するために奇妙な問題がたくさんありました:)ここハンガリーでは、私は小数点としてカンマを使用しています...(私は、たとえこの状況がトラブルを引き起こす可能性があることを最初に知ったときに、私の最も尊敬される同僚の前でさえ、非政治的に正しい表現を大声で言った...) – ppeterka

+0

はいどのような種類のバグでも "wtf-situation"が作成されます... –

0

この書式文字列が修正されました。

"INSERT INTO tops VALUES (%f, '%s', %f, %.2f, '%s', TO_TIMESTAMP('%s', 'YYYY-MM-DD HH24:MI:SS.FF'))" 

各引数には多くの値を使用しないで、それぞれ1つずつ、合計6つの値を使用してください。

関連する問題