private void CommitMergedDeletes(MergePolicy.OneMerge merge, SegmentReader mergeReader)
{
lock (this)
{
System.Diagnostics.Debug.Assert(TestPoint("startCommitMergeDeletes"));
SegmentInfos sourceSegments = merge.segments;
if (infoStream != null)
Message("commitMergeDeletes " + merge.SegString(directory));
// Carefully merge deletes that occurred after we
// started merging:
int docUpto = 0;
int delCount = 0;
for (int i = 0; i < sourceSegments.Count; i++)
{
SegmentInfo info = sourceSegments.Info(i);
int docCount = info.docCount;
SegmentReader previousReader = merge.readersClone[i];
SegmentReader currentReader = merge.readers[i];
if (previousReader.HasDeletions)
{
// There were deletes on this segment when the merge
// started. The merge has collapsed away those
// deletes, but, if new deletes were flushed since
// the merge started, we must now carefully keep any
// newly flushed deletes but mapping them to the new
// docIDs.
if (currentReader.NumDeletedDocs > previousReader.NumDeletedDocs)
{
// This means this segment has had new deletes
// committed since we started the merge, so we
// must merge them:
for (int j = 0; j < docCount; j++)
{
if (previousReader.IsDeleted(j))
{
System.Diagnostics.Debug.Assert(currentReader.IsDeleted(j));
}
else
{
if (currentReader.IsDeleted(j))
{
mergeReader.DoDelete(docUpto);
delCount++;
}
docUpto++;
}
}
}
else
{
docUpto += docCount - previousReader.NumDeletedDocs;
}
}
else if (currentReader.HasDeletions)
{
// This segment had no deletes before but now it
// does:
for (int j = 0; j < docCount; j++)
{
if (currentReader.IsDeleted(j))
{
mergeReader.DoDelete(docUpto);
delCount++;
}
docUpto++;
}
}
// No deletes before or after
else
docUpto += info.docCount;
}
System.Diagnostics.Debug.Assert(mergeReader.NumDeletedDocs == delCount);
mergeReader.hasChanges = delCount > 0;
}
}