簡體   English   中英

是否有轉換IList的方法 <ArraySegment<byte> &gt;到byte []而不通過列表枚舉並添加到新的byte []嗎?

[英]Is there a away to convert IList<ArraySegment<byte>> to byte[] without enumerating through the List and adding to a new byte[]?

我了解我可以通過IList進行枚舉,例如:

public byte[] ConvertToByteArray(IList<ArraySegment<byte>> list) {
    IList<byte> newList = new List<byte>();
    foreach(var asb in list) {
       for ( int i = asb.Offset; i < (asb.Offset + asb .Count); i++ )  {
           newList.Add(asb.Array[i]);
       }
    }
    return newList.ToArray();
}

但這看起來很丑,有沒有更好的方法呢?

這可以是一個潛在的棘手的問題,因為ArraySegment實際上僅僅圍繞原始陣列的圖包裝,並沒有限制的數量ArraySegment (一個或多個創建的周圍排列的被存儲為參考,不是副本,在ArraySegment.Array屬性)-因此,您不能ArraySegment.Array提取數組來做任何技巧。

話雖如此,您的初始代碼可以稍作改進。 緩沖副本。 假定您要使指向基礎數組中相同值的段中的值在結果數組中重復。

public byte[] ConvertToByteArray(IList<ArraySegment<byte>> list)
{
    var bytes = new byte[list.Sum (asb => asb.Count)];
    int pos = 0;

    foreach (var asb in list) {
        Buffer.BlockCopy (asb.Array, asb.Offset, bytes, pos, asb.Count);
        pos += asb.Count;
    }

    return bytes;
}

這樣做確實在list上進行了兩次迭代(以獲取總計數,但是對於更大的ArraySegments,在我的綜合測試中,緩沖復制是一次成功,而不是額外的迭代是一次失敗)。 與往常一樣,測量其性能關鍵代碼路徑。

一次遇到同一問題時,我發現了這個很好的解釋您的問題。 http://www.fotia.co.uk/fotia/DN.01.CoVariantGenericList.aspx

通過創建從通用列表類繼承的類並添加為我執行迭代的構造函數,我已經實現了您可能希望使用的代碼類型。

public class bytes : List<byte>
{
    public bytes()
    {
    }

    public bytes (IList<ArraySegment<byte>> list)
    {
       for ( int i = 0; i < list.Count; i++ )  
       {
           this.Add(asb.Array[i]);
       }        
    }
}

然后,在您的代碼中就可以擁有:

bytes myList = new bytes(yourIList);

這不會消除對轉換的需求,但會隱藏代碼。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM