private (DataHeader Header, Data Info) InsertInfo(int DataLen, int Pos) { var TotalLen = DataLen + HeadSize; Data Gap; Data Data; if (PopGapMinLen(TotalLen, out Gap) == false)//// haven't free gap { var StreamLen = (int)Stream.Length; Stream.AddLen(TotalLen); Data = new Data() { From = StreamLen, Len = TotalLen, To = StreamLen + TotalLen - 1 }; } else { Data = new Data() { From = Gap.From, Len = TotalLen, To = Gap.From + TotalLen - 1 }; if (Gap.Len > TotalLen) { Gap.Len = Gap.Len - TotalLen; Gap.From = Gap.From + TotalLen; var NextGap = Gap; if (PopNextGap(ref NextGap)) { Gap.Len += NextGap.Len; Gap.To = NextGap.To; } InsertGap(Gap); } } var Header = new DataHeader(); Header.DataLen = Data.Len; Keys.Insert(Data, Pos); if (Keys.Length == Pos + 1) { Header.NextData = -1; } else { Header.NextData = Keys[Pos + 1].From; } return(Header, Data); }
public StreamCollection(System.IO.Stream Stream, int MinCount = 5000) { this.Stream = new DataWork.StreamController(Stream, 4, MinCount); { Keys = new Array <Data>(); GapsByFrom = new Array <DataByForm>(); GapsByLen = new Array <DataByLen>(); GapsByTo = new Array <DataByTo>(); var NextPos = BitConverter.ToInt32(this.Stream.GetHeader()); NextPos--; if (NextPos != -1) { while (NextPos != -1) { this.Stream.Seek(NextPos, System.IO.SeekOrigin.Begin); var Header = this.Stream.Read(HeadSize).Deserialize <DataHeader>(); Keys.Insert(new Data() { From = NextPos, Len = Header.DataLen, To = NextPos + Header.DataLen }); NextPos = Header.NextData; } Length = Keys.Length; var NewDatas = new Array <Data>(); NewDatas.BinaryInsert(Keys.ToArray()); var CurrentPos = 0; for (int i = 0; i < NewDatas.Length; i++) { var NewData = NewDatas[i]; if (CurrentPos != NewData.From) { InsertGap(new Data() { From = CurrentPos, Len = (NewData.From - CurrentPos), To = NewData.From - 1 }); } CurrentPos = NewData.To + 1; } } } Keys.ChangedNextSequence = (c) => { if (c.Before == null) { if (Keys.Length > 0) { this.Stream.SetHeader(BitConverter.GetBytes(Keys[0].From + 1)); } else { this.Stream.SetHeader(BitConverter.GetBytes(0)); } } else { var Data = c.Before.Value; var Header = new DataHeader(); Header.DataLen = Data.Len; if (c.Next == null) { Header.NextData = -1; } else { Header.NextData = c.Next.Value.From; } var Stream = this.Stream; Stream.Seek(Data.From, System.IO.SeekOrigin.Begin); Stream.Write(Header.Serialize(), 0, HeadSize); } }; }