我有这个代码将Treemap转换为字节并将它们存储在数据库中(Oracle 11g)。现在存储似乎工作正常。我想现在检索地图,但它在blob字段中以字节为单位。如何检索和重新构建地图?
存储地图的代码是:
public void StoreMapDB(TreeMap<DateTime, Integer> map) throws
IOException, FileNotFoundException{
try {
Connection con = null;
Class.forName("oracle.jdbc.driver.OracleDriver");
con=DriverManager.getConnection(
"jdbc:oracle:thin:@dsds",
"dsdsd",
"XXdsdsX");
con.setAutoCommit(false);
ByteArrayOutputStream bos = new ByteArrayOutputStream() ;
ObjectOutputStream out = new ObjectOutputStream(bos);
out = new ObjectOutputStream(bos) ;
out.writeObject(map);
out.close();
byte[] buf = bos.toByteArray();
PreparedStatement prepareStatement = con.prepareStatement("INSERT INTO
SMD_DATESTREEMAP VALUES(?,?)");
prepareStatement.setLong(1, 2);
prepareStatement.setBinaryStream(2, new ByteArrayInputStream(buf),
buf.length);
prepareStatement.executeUpdate();
// insertMap.executeUpdate();
con.commit();
} catch(Exception e){
System.err.print(e);
}
}
P.S。我编辑了这段代码但不认为它有效,因为它将检索到的地图的大小显示为0,它应该是366。
public TreeMap<DateTime, Integer> retrieveMapDB()throws IOException,
SQLException{
try {
Connection con = null;
Class.forName("oracle.jdbc.driver.OracleDriver");
con=DriverManager.getConnection(
"jdbc:oracle:thin:@oradbfdfdt05:f:fdfd",
"cxcx",
"hpdbcxcxsmb");
con.setAutoCommit(false);
ResultSet rs = null;
PreparedStatement pstmt = null;
String query = "SELECT TREEMAP FROM SMD_DATESTREEMAP WHERE id = ?";
try {
pstmt = con.prepareStatement(query);
int id = 1;
pstmt.setInt(1, id);
rs = pstmt.executeQuery();
while(rs.next()){
ByteArrayInputStream bos = new
ByteArrayInputStream(rs.getBytes("TREEMAP")) ;
ObjectInputStream out = new ObjectInputStream(bos);
retrievedmap=(TreeMap<DateTime, Integer>)out.readObject();
}
}catch(IOException ioe){
System.err.print(ioe);
}
}catch(ClassNotFoundException cnfe){
System.err.print(cnfe);
}
return retrievedmap;
}
答案 0 :(得分:2)
您可以通过ResultSet.getBinaryStream()
方法获取InputStream对象。
PreparedStatement prepareStatement = con.prepareStatement("select * from SMD_DATESTREEMAP");
ResultSet rs=prepareStatement.executeQuery();
while(rs.next())
{
oracle.jdbc.driver.OracleBlobInputStream bos=(oracle.jdbc.driver.OracleBlobInputStream) rs.getBinaryStream(2) ;
ObjectInputStream out = new ObjectInputStream(bos);
map=(TreeMap<DateTime, Integer>)out.readObject();
...
}
您可以编写字节数组而不是二进制流。
ByteArrayOutputStream bos = new ByteArrayOutputStream() ;
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(map);
out.flush();
out.close();
byte[] buf = bos.toByteArray();
PreparedStatement prepareStatement = con.prepareStatement("INSERT INTO SMD_DATESTREEMAP VALUES(?,?)");
prepareStatement.setInt(1, 1);
prepareStatement.setBytes(2, buf);
prepareStatement.executeUpdate();
prepareStatement.close();
并读取字节数组:
while(rs.next())
{
byte []buf=rs.getBytes(2);
ByteArrayInputStream bos=new ByteArrayInputStream(buf);
ObjectInputStream out = new ObjectInputStream(bos);
map=(TreeMap<DateTime, Integer>)out.readObject();
..
}
答案 1 :(得分:1)
感谢AVD的大力支持,这对我的代码/问题也起了最大的作用。所以答案就在这里...... BLOB from Oracle
与AVD的答案相辅相成的片段是:
Blob blob = rs.getBlob("col_blob");
// Get the number bytes in the BLOB
long blobLength = blob.length();
// Get bytes from the BLOB in a byte array
int pos = 1; // position is 1-based
int len = 10;
byte[] bytes = blob.getBytes(pos, len);
希望这会有所帮助,如果有人要求澄清,我将不仅仅是快乐:D