目前我遇到了一個非常令人沮喪的問題。我會盡量抽象出這個問題,讓它更容易一些。它必須在一個進程中將我的自定義對象序列化到數據庫,並在另一個進程中對其進行反序列化。反序列化MemoryStream - 出乎意料的行爲
我有兩個組件; AppToDB.dll
和AppFromDB.dll
。我有第三個程序集 - MyCustomObject.dll
- 這兩個程序集都包含一個引用。 MyCustomObject.dll
延伸MarshalByRefObject
。
在我AppToDB.dll
我執行下面的代碼:
public bool serializeToDB(MyCustomObject obj)
{
OdbcDataAdapter da = new OdbcDataAdapter();
MemoryStream memStream = new MemoryStream();
try
{
ObjRef marshalledObj = RemotingServices.Marshal((System.MarshalByRefObject)obj);
// Serialize the object; construct the desired formatter
IFormatter oBFormatter = new BinaryFormatter();
// Try to serialize the object
oBFormatter.Serialize(memStream, marshalledObj);
// Create byte array
byte[] serialized = memStream.ToArray();
// Build the query to write to the database
string queryString =
"INSERT INTO MyCustomObject(id, object) VALUES(?, ?)";
OdbcCommand command = new OdbcCommand(queryString, connection);
command.Parameters.AddWithValue("id", 1);
command.Parameters.AddWithValue("object", serialized);
// Write the object byte array to the database
int num = command.ExecuteNonQuery();
}
catch { }
}
在AppFromDB.dll
我執行此代碼:
public OCR.Batch deserializeFromDB()
{
MemoryStream memStream = new MemoryStream();
try
{
string queryString = "SELECT object FROM FCBatch";
OdbcCommand command = new OdbcCommand(queryString, connection);
OdbcDataReader reader = command.ExecuteReader(CommandBehavior.SequentialAccess);
// Size of the BLOB buffer.
int bufferSize = 100;
// The BLOB byte[] buffer to be filled by GetBytes.
byte[] outByte = new byte[bufferSize];
// The bytes returned from GetBytes.
long retval;
// The starting position in the BLOB output.
long startIndex = 0;
MemoryStream dbStream = new MemoryStream();
while (reader.Read())
{
// Reset the starting byte for the new BLOB.
startIndex = 0;
// Read bytes into outByte[] and retain the number of bytes returned.
retval = reader.GetBytes(0, startIndex, outByte, 0, bufferSize);
// Continue while there are bytes beyond the size of the buffer.
while (retval == bufferSize)
{
dbStream.Write(outByte, 0, bufferSize);
dbStream.Flush();
// Reposition start index to end of last buffer and fill buffer.
startIndex += bufferSize;
retval = reader.GetBytes(0, startIndex, outByte, 0, bufferSize);
}
// Write the remaining buffer.
dbStream.Write(outByte, 0, (int)retval);
dbStream.Flush();
}
// Close the reader and the connection.
reader.Close();
dbStream.Position = 0;
object temp = oBFormatter.Deserialize(dbStream);
MyCustomObject obj = (MyCustomObject)temp;
return null;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
return null;
}
}
OK,所以在這兩個代碼段,你可以看到一個MemoryStream
對象。在第一個AppToDB
它被創建,如果我看它的內容它包含707個字節。精細。我將它寫入數據庫並將其保存爲BLOB。現在在AppFromDB
我檢索BLOB並將其存儲在byte[]
陣列中。我再次將byte[]
數組寫入MemoryStream
,並看到我的MemoryStream
對象包含707個字節,所有這些都與原始位置一樣。看來我已經成功轉移了這個對象!
現在問題在於object temp = oBFormatter.Deserialize(dbStream);
。只要我嘗試反序列化,我的object
是透明代理,我無法投射到MyCustomObject
!我如何獲得我的原始對象?如何在#@ &的名稱可以有一個MemoryStream對象....在內存中...準備好被序列化...突然它又是一個透明代理服務器。
我不知所措。幫助表示讚賞。我會祈求#@ &對於誰擁有了答案之一;)
編輯1 OK,我必須說,事情開始變得有意義,現在(雖然問題仍然存在)。我的問題:我在一邊有一個對象(包括狀態),我需要將它存儲在數據庫中,以便日後可以在另一端使用另一個進程。
我的對象不可序列化,因爲它包裝了未標記爲可序列化的第三方對象。所以我唯一的選擇似乎是編組,它返回一個ObjRef,它反過來是可序列化的。但是當然 - 幾天之後 - 我反序列化的對象僅僅是參考,我的原始對象已經消失了。
我該如何解決我的問題?更多的人一定都遇到過這一點,我似乎無法找到答案......
編輯2 OK,我想我會寫我自己的序列化的類同構於第三方對象。然後運行整個第三方對象,並存儲/包裝其狀態信息等,然後序列化我的對象到數據庫...似乎是我唯一的選擇。
編輯3 過了一段時間再次開始這個問題。剛剛意識到,雖然解決方案張貼在編輯2將無法正常工作。我必須反序列化第三方程序集所知道的對象,因爲它將繼續對它執行操作。
可能重複[如何編組對象及其內容(也是對象)](http://stackoverflow.com/questions/3068702/how-to-marshal-an-object-and-its- content-also-objects) – Lucero 2010-06-23 19:31:47