引起:java.lang.ClassCastException:java.sql.Timestamp 不能转换为 java.sql.Date
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/25892417/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Caused by: java.lang.ClassCastException: java.sql.Timestamp cannot be cast to java.sql.Date
提问by being_uncertain
I am getting the below given error for the following code snippets:
对于以下代码片段,我收到以下给定错误:
try {
cRows = new CachedRowSetImpl();
while(cRows.next())
{
MyClass myClass = new MyClass();
myClass.setPrevDate(cRows.getDate("PREV_DATE")); // In debug mode, the error was throwing when I press Resume from here.
}
}
Error:
错误:
Caused by: java.lang.ClassCastException: java.sql.Timestamp cannot be cast to java.sql.Date
In the database, the datatype for the column is DATE
only. I am not able to figure out where the Timestamp
is coming here.
在数据库中,列的数据类型DATE
仅为。我不知道Timestamp
从哪里来。
采纳答案by being_uncertain
I have done a research on this issue and found some useful links. I found this confusion between DATE and TIMESTAMP is JDBC Driver specific. And most of the links suggest the use of -Doracle.jdbc.V8Compatible=true
. For my JBoss I have set this in run.bat
and the issue got resolved.
我已经对这个问题进行了研究,并找到了一些有用的链接。我发现 DATE 和 TIMESTAMP 之间的这种混淆是特定于 JDBC 驱动程序的。大多数链接都建议使用-Doracle.jdbc.V8Compatible=true
. 对于我的 JBoss,我已经设置了它run.bat
并且问题得到了解决。
http://www.coderanch.com/t/90891/JBoss/oracle-jdbc-Compatible-true
- https://community.oracle.com/message/3613155
http://www.coderanch.com/t/90891/JBoss/oracle-jdbc-Compatible-true
- https://community.oracle.com/message/3613155
The oracle doc shares different solutions:
oracle doc 分享了不同的解决方案:
Alter your tables to use TIMESTAMP instead of DATE. This is probably rarely possible, but it is the best solution when it is.
Alter your application to use defineColumnType to define the columns as TIMESTAMP rather than DATE. There are problems with this because you really don't want to use defineColumnType unless you have to (see What is defineColumnType and when should I use it? ).
Alter you application to use getTimestamp rather than getObject. This is a good solution when possible, however many applications contain generic code that relies on getObject, so it isn't always possible.
Set the V8Compatible connection property. This tells the JDBC drivers to use the old mapping rather than the new one. You can set this flag either as a connection property or a system property. You set the connection property by adding it to the java.util.Properties object passed to DriverManager.getConnection or to OracleDataSource.setConnectionProperties. You set the system property by including a -D option in your java command line.
java -Doracle.jdbc.V8Compatible="true" MyApp
更改您的表以使用 TIMESTAMP 而不是 DATE。这可能很少可能,但它是最好的解决方案。
更改您的应用程序以使用defineColumnType 将列定义为TIMESTAMP 而不是DATE。这有问题,因为除非必须,否则您真的不想使用defineColumnType(请参阅什么是defineColumnType 以及何时应使用它?)。
更改您的应用程序以使用 getTimestamp 而不是 getObject。如果可能,这是一个很好的解决方案,但是许多应用程序包含依赖于 getObject 的通用代码,因此它并不总是可行的。
设置 V8Compatible 连接属性。这告诉 JDBC 驱动程序使用旧映射而不是新映射。您可以将此标志设置为连接属性或系统属性。您可以通过将连接属性添加到传递给 DriverManager.getConnection 或 OracleDataSource.setConnectionProperties 的 java.util.Properties 对象来设置它。您可以通过在 java 命令行中包含 -D 选项来设置系统属性。
java -Doracle.jdbc.V8Compatible="true" MyApp
Here is the link: http://www.oracle.com/technetwork/database/enterprise-edition/jdbc-faq-090281.html#08_00
这是链接:http: //www.oracle.com/technetwork/database/enterprise-edition/jdbc-faq-090281.html#08_00
回答by Joop Eggen
Obsolete:
过时的:
Use java.util.Date
for the field.java.sql.Timestamp
is a direct subclass of it. As is java.sql.Date
- that strips the time part. Why the java database driver takes DATE to be Timestamp is a bit weird. What is the database vendor? Did you specify a length or so? Are indeed only dates stored?
使用java.util.Date
该字段。java.sql.Timestamp
是它的直接子类。按java.sql.Date
原样 - 去掉时间部分。为什么 java 数据库驱动程序将 DATE 设为 Timestamp 有点奇怪。什么是数据库供应商?你指定了一个长度吗?确实只存储日期吗?
Researched:
研究过:
I looked into CachedRowSetImpl.java, and Oracle's docs and Oracle does everything fine (java.sql.Date, java.sql.Time, java.sql.Timestamp convertible). The CachedRowSetImpl does simply cast the DATE's Object (and getObject is likely to return the high resolution Timestamp - with time) to java.sql.Date, and that's wrong. So overrideor substitutethis sun's class.
我查看了CachedRowSetImpl.java,Oracle 的文档和 Oracle 一切都很好(java.sql.Date、java.sql.Time、java.sql.Timestamp 可转换)。CachedRowSetImpl 只是将 DATE 的对象(并且 getObject 可能返回高分辨率时间戳 - 随时间)到 java.sql.Date,这是错误的。所以覆盖或替换这个太阳的类。
/*
* The object coming back from the db could be
* a date, a timestamp, or a char field variety.
* If it's a date type return it, a timestamp
* we turn into a long and then into a date,
* char strings we try to parse. Yuck.
*/
switch (RowSetMD.getColumnType(columnIndex)) {
case java.sql.Types.DATE: {
long sec = ((java.sql.Date)value).getTime();
return new java.sql.Date(sec);
}