使用线段树查找重叠区间的总长度?
Posted
技术标签:
【中文标题】使用线段树查找重叠区间的总长度?【英文标题】:Find the total length of overlapped intervals using segment tree? 【发布时间】:2013-01-25 13:31:52 【问题描述】:我们有一些区间,例如 [1;4] [7;13] [9;14] 输入应该返回 3+6+1=10。 在可以动态插入或删除区间的情况下,有什么方法可以使用线段树来找到这些区间的总长度?
P.S.:我想在不使用段树的情况下这样做,但时间复杂度并不让我满意。
提前谢谢你
【问题讨论】:
您有多少个间隔以及最大最小位置和迭代长度。有多少请求得到总和,有多少插入? 间隔是否按照您的示例进行排序? @AndyT 是的,我可以先对它们进行排序 区间可以动态插入或删除。 【参考方案1】:假设间隔存储在数组[m,n] 中。 另一个假设是数组已排序。
您需要做的就是找到较小的差异:
int totalIntervales = 0;
for(int index = 0; index < array.length ; index++)
int currentIntrval = array[index, 1] - array[index, 0];
int differnceFromPrevious = array[index, 1] - array[index- 1, 1]
totalIntervale += currentIntrval > differnceFromPrevious ? differnceFromPrevious : currentIntrval;
return totalIntervale;
小心处理 0 位置。
【讨论】:
我认为当第二个区间完全包含在第一个区间内时,您的算法存在错误。考虑集合 [1,4][2,3]。您的算法会说间隔为 2。解决方法是检查 differenceFromPrevious 是否为非负数。否则,它似乎工作。 (编辑因为我忘记点击“输入”会提交评论) 实际上,经过进一步考虑,我认为您的算法效果不佳。以 [1, 5][1, 2][2, 4] 为例。您的算法会报告 4 - 3 + 2 = 3。【参考方案2】:Kobi/Maureinik 的答案非常接近,但我必须为 maxEnd 添加一个变量并检查 differenceFromPrevious 是否为非负数。该算法仍然假设范围是在开始元素上排序的(即 array[i, 0])
int totalInterval = array[0, 1] - array[0, 0];
int maxEnd = array[0, 1];
for(int index = 1; index < array.length ; index++)
int currentIntrval = array[index, 1] - array[index, 0];
int differnceFromPrevious = array[index, 1] - maxEnd;
if(differenceFromPrevious >= 0)
totalInterval += (currentIntrval > differnceFromPrevious) ? differnceFromPrevious : currentIntrval;
maxEnd = (maxEnd >= array[index, 1]) ? maxEnd : array[index, 1];
return totalInterval;
编辑:修复了无效的原始 totalInterval 逻辑的意外副本。如果 differenceFromPrevoius
【讨论】:
以上是关于使用线段树查找重叠区间的总长度?的主要内容,如果未能解决你的问题,请参考以下文章