我尝试将数据从一个表的字符串字段放入另一个表的数字字段。
如果我在 Oracle SQL Developer 或 Toad 等 IDE 中执行此操作,它可以正常工作,但如果我在我的 java 代码中执行此操作,则会出现错误。
如何解决?
下面有我的例子。
数据库:我创建了两个表 - 带有数字字段的 t_num 和带有 varchar2 字段的 t_str - 并将值放入第二个表 t_str
drop table t_num;
create table t_num(num number(10,2));
drop table t_str;
create table t_str(str varchar2(10));
insert into t_str (str) values('23');
insert into t_str (str) values('2 3');
insert into t_str (str) values('2 3,3 2');
commit;
我还创建了将值从 t_str 放到 t_num 的过程
create or replace procedure put_to_t_num
as
type t_num_t is table of t_num%rowtype index by binary_integer;
tn t_num_t;
n binary_integer := 0;
begin
delete from t_num;
--tn := t_num_t();
for rec in ( select * from t_str )
loop
n := n + 1;
--tn.extend;
tn(n).num := to_number( regexp_replace( regexp_replace( rec.str, ',', '.'), ' ', '' ) );
end loop;
forall i in 1..n
insert into t_num (
num
) values (
tn(i).num
);
--commit;
end;
网络逻辑服务器:
index.jsp:点击按钮向put.jsp发送请求
<button>click</button>
<script>
document.querySelector("button").addEventListener("click", function () {
var xhr = new XMLHttpRequest();
xhr.open("GET", "put.jsp");
xhr.send(null);
xhr.onreadystatechange = function () {
if (xhr.readyState == xhr.DONE && xhr.status == 200) {
console.log(xhr.responseText);
}
}
});
</script>
put.jsp:从具有 jndi 名称 jdbc/test 的数据源获取连接并调用过程 put_to_t_num
<%@ page contentType="text/html; charset=UTF-8"%>
<%@ page trimDirectiveWhitespaces="true"%>
<%@ page import="javax.annotation.Resource"%>
<%!
@Resource(name="jdbc/test")
private DataSource ds = null;
%>
<%@ page import="javax.sql.*"%>
<%@ page import="java.sql.*"%>
<%@ page import="javax.naming.*"%>
<%@ page import="java.util.*"%>
<%
Context ctx = null;
try {
ctx = new InitialContext();
ds = (DataSource) ctx.lookup("jdbc/test");
} catch (Exception e) {
out.print(e.getMessage());
}
Connection con = null;
CallableStatement cstmt = null;
Statement stmt = null;
try {
//call procedure
con = ds.getConnection();
cstmt = con.prepareCall("{call put_to_t_num}");
cstmt.execute();
//commit
stmt = con.createStatement();
stmt.executeUpdate("commit");
out.print("success");
} catch (SQLException e) {
out.print("catch error:\n" + e.getMessage());
} finally {
try {
if (cstmt != null) {
cstmt.close();
}
if (stmt != null) {
stmt.close();
}
if (con != null) {
con.close();
}
} catch (Exception e) {
out.print("finally error:\n" + e.getMessage());
}
}
%>
最后我在浏览器控制台中遇到错误:
catch error:
ORA-06502: PL/SQL: numeric or value error: character to number conversion error
ORA-06512: at "TEST_USER.PUT_TO_T_NUM", line 13
ORA-06512: at line 1
但是如果我在 IDE 中做这样的事情,它工作得很好
begin
put_to_t_num;
commit;
end;
我想这可能是编码的情况,但我无法在我的 java 代码中解决它。
select * from nls_database_parameters;
NLS_LANGUAGE AMERICAN
NLS_TERRITORY AMERICA
NLS_CURRENCY $
NLS_ISO_CURRENCY AMERICA
NLS_NUMERIC_CHARACTERS .,
NLS_CHARACTERSET AL32UTF8
NLS_CALENDAR GREGORIAN
NLS_DATE_FORMAT DD-MON-RR
NLS_DATE_LANGUAGE AMERICAN
NLS_SORT BINARY
NLS_TIME_FORMAT HH.MI.SSXFF AM
NLS_TIMESTAMP_FORMAT DD-MON-RR HH.MI.SSXFF AM
NLS_TIME_TZ_FORMAT HH.MI.SSXFF AM TZR
NLS_TIMESTAMP_TZ_FORMAT DD-MON-RR HH.MI.SSXFF AM TZR
NLS_DUAL_CURRENCY $
NLS_COMP BINARY
NLS_LENGTH_SEMANTICS BYTE
NLS_NCHAR_CONV_EXCP FALSE
NLS_NCHAR_CHARACTERSET AL16UTF16
NLS_RDBMS_VERSION 11.2.0.2.0
如何解决这个问题?
我还发现,如果没有将值 2 3,3 2 添加到 t_str - 我得到了“成功”。
我该如何处理这种情况?
为什么IDE会这样做,而java代码却不这样做?