[英]c# improve binary serialization
我目前正在從事一個基於其他代碼生成代碼的項目。 本質上是將編程語言本身用作DSL。
生成器目標之一是二進制DataContract序列化程序,以及為以下類生成的ToBytes
[DataContract]
public partial class Root
{
[DataMember]
public int Number { get; set; }
[DataMember]
public Partial[] Partials { get; set; }
[DataMember]
public IList<ulong> Numbers { get; set; }
}
變成這個:
public int Size
{
get
{
var size = 8;
// Add size for collections and strings
size += Partials.Sum(entry => entry.Size);
size += Numbers.Count * 8;
return size;
}
}
public byte[] ToBytes()
{
var index = 0;
var bytes = new byte[Size];
return ToBytes(bytes, ref index);
}
public byte[] ToBytes(byte[] bytes, ref int index)
{
// Convert Number
Buffer.BlockCopy(BitConverter.GetBytes(Number), 0, bytes, index, 4);;
index += 4;
// Convert Partials
// Two bytes length information for each dimension
Buffer.BlockCopy(BitConverter.GetBytes((ushort)(Partials == null ? 0 : Partials.Length)), 0, bytes, index, 2);
index += 2;
foreach(var value in Partials ?? Enumerable.Empty<Partial>())
{
value.ToBytes(bytes, ref index);
}
// Convert Numbers
// Two bytes length information for each dimension
Buffer.BlockCopy(BitConverter.GetBytes((ushort)(Numbers == null ? 0 : Numbers.Count)), 0, bytes, index, 2);
index += 2;
foreach(var value in Numbers ?? Enumerable.Empty<ulong>())
{
Buffer.BlockCopy(BitConverter.GetBytes(value), 0, bytes, index, 8);;
index += 8;
}
return bytes;
}
現在,即使這變得非常困難,我也正在尋找一種方法來加速Buffer.BlockCopy(BitConverter.GetBytes
所有使用。為每次轉換創建一個新的小byte[]
然后復制它似乎仍然浪費資源。當我都准備好了byte[]
和位置的時候。
有什么想法可以最好地改進代碼嗎?
更新:基於@adrianm注釋,我將用數組的for循環替換foreach並將可空類型包裝在if語句中。 不需要在另一個線程中使用結構。 我寧願使用類和[DataContract]屬性。 另外,為了符合Linux,我不能使用WinApi。
Update2:添加了其余的生成代碼。 感謝您的評論,將來的版本將包括
if (index + Size > bytes.Length)
// Some error handling
因此,我看到了BitConverter的實現以及它們對unsafe和指針的使用,以創建byte[]
。 我想在生成的代碼中使用它,例如:
*byte pointer = bytes;
*((int*)pointer + pos) = Number;
pos += 4;
但是在那種情況下,這將是一種不安全的方法,並且我不確定這將對那里的更多托管代碼產生什么影響。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.