예제 #1
0
        /// <summary>
        /// Creates a union stream reader from the supplied data.
        /// </summary>
        /// <param name="streams">all of the tables to combine in the union</param>
        /// <param name="ownsStream">if this class owns the streams, it will call dispose when <see cref="Dispose"/> is called.
        /// Otherwise, the streams will not be disposed.</param>
        public UnionTreeStream(IEnumerable <TreeStream <TKey, TValue> > streams, bool ownsStream)
        {
            m_firstStream    = null;
            m_ownsStreams    = ownsStream;
            m_tablesOrigList = streams.Select(x => new BufferedTreeStream(x)).ToArray();

            m_sortedArchiveStreams = new UnionTreeStreamSortHelper(m_tablesOrigList);
            m_readWhileUpperBounds.SetMin();

            foreach (var table1 in m_sortedArchiveStreams.Items)
            {
                table1.EnsureCache();
            }
            m_sortedArchiveStreams.Sort();

            //Remove any duplicates
            RemoveDuplicatesIfExists();

            if (m_sortedArchiveStreams.Items.Length > 0)
            {
                m_firstTable = m_sortedArchiveStreams[0];
            }
            else
            {
                m_firstTable = null;
            }

            SetReadWhileUpperBoundsValue();
        }
 public void Dispose()
 {
     if (Stream != null)
     {
         Stream.Dispose();
         Stream = null;
     }
 }
        /// <summary>
        /// Creates a <see cref="DistinctTreeStream{TKey,Value}"/>
        /// </summary>
        /// <param name="baseStream">Must be sequential</param>
        public DistinctTreeStream(TreeStream <TKey, TValue> baseStream)
        {
            if (!baseStream.IsAlwaysSequential)
            {
                throw new ArgumentException("Must be sequential access", "baseStream");
            }

            m_lastKey          = new TKey();
            m_lastValue        = new TValue();
            m_isLastValueValid = false;
            m_baseStream       = baseStream;
        }
            /// <summary>
            /// Creates the table reader.
            /// </summary>
            /// <param name="stream"></param>
            public BufferedTreeStream(TreeStream <TKey, TValue> stream)
            {
                if (!stream.IsAlwaysSequential)
                {
                    throw new ArgumentException("Stream must gaurentee sequential data access");
                }
                if (!stream.NeverContainsDuplicates)
                {
                    stream = new DistinctTreeStream <TKey, TValue>(stream);
                }

                Stream = stream;
                EnsureCache();
            }
예제 #5
0
        private bool Read2(TKey key, TValue value)
        {
TryAgain:
            if (m_firstStream == null)
            {
                //If m_firstStream == null, this means either:
                //  the value is cached.
                // or
                //  the end of the stream has occured.
                if (m_firstTable != null && m_firstTable.IsValid)
                {
                    //The value is cached.
                    m_firstTable.Read(key, value);
                    m_firstStream = m_firstTable.Stream;
                    return(true);
                }
                //The end of the steam has been reached.
                return(false);
            }

            //Condition 1:
            //  The archive stream may no longer be in order and needs to be checked
            //Response:
            //  Resort the archive stream
            //
            //Condition 2:
            //  The end of the frame has been reached
            //Response:
            //  Advance to the next frame
            //  Also test the edge case where the current point might be equal to the end of the frame
            //      since this is an inclusive filter and ReadWhile is exclusive.
            //      If it's part of the frame, return true after Advancing the frame and the point.
            //

            //Since condition 1 and 2 can occur at the same time, verifying the sort of the Archive Stream is a good thing to do.
            // Will verify that the stream is in the proper order and remove any duplicates that were found.
            // May be called after every single read, but better to be called
            // when a ReadWhile function returns false.

            if (m_sortedArchiveStreams.Items.Length > 1)
            {
                //If list is no longer in order
                int compare = CompareStreams(m_sortedArchiveStreams[0], m_sortedArchiveStreams[1]);
                if (compare == 0) //A duplicate value was found.
                {
                    //If a duplicate entry is found, advance the position of the duplicate entry
                    RemoveDuplicatesFromList();
                    SetReadWhileUpperBoundsValue();

                    m_firstTable = m_sortedArchiveStreams[0];
                }
                else if (compare > 0) //List is out of order
                {
                    m_sortedArchiveStreams.SortAssumingIncreased(0);
                    m_firstTable = m_sortedArchiveStreams[0];
                    SetReadWhileUpperBoundsValue();
                }
            }
            else
            {
                //If only 1 stream, we can't resort, so we are done.
                if (!m_sortedArchiveStreams[0].IsValid)
                {
                    return(false);
                }
            }

            m_firstStream = null; //Ensure that the if block is executed when repeating this function call.
            goto TryAgain;
        }