Javascript 如何在一组持续时间中找到常见的重叠?
我有一组持续时间(使用但乐于使用本机代码或其他东西),如下所示:Javascript 如何在一组持续时间中找到常见的重叠?,javascript,node.js,momentjs,duration,Javascript,Node.js,Momentjs,Duration,我有一组持续时间(使用但乐于使用本机代码或其他东西),如下所示: 2018-06-19T09:00:00Z - 2018-06-19T10:00:00Z 2018-06-19T09:30:00Z - 2018-06-19T10:30:00Z 2018-06-19T09:30:00Z - 2018-06-19T11:00:00Z 2018-06-19T10:00:00Z - 2018-06-19T11:00:00Z 这看起来像: 09:00 ..+-+.................
2018-06-19T09:00:00Z - 2018-06-19T10:00:00Z
2018-06-19T09:30:00Z - 2018-06-19T10:30:00Z
2018-06-19T09:30:00Z - 2018-06-19T11:00:00Z
2018-06-19T10:00:00Z - 2018-06-19T11:00:00Z
这看起来像:
09:00 ..+-+.................
| |
09:30 ..| |..+-+..+-+.......
| | | | | |
10:00 ..+-+..| |..| |..+-+..
| | | | | |
10:30 .......+-+..| |..| |..
| | | |
11:00 ............+-+..+-+..
我想要一个算法来找到至少3个(或x个)持续时间重叠的持续时间。在上述示例中,有两个持续时间符合此标准:
2018-06-19T09:30:00Z - 2018-06-19T10:00:00Z
2018-06-19T10:00:00Z - 2018-06-19T10:30:00Z
我花了很长时间试图解决这个问题,特别是使用“力矩范围”,但我完全不知所措
更新
鉴于该问题被否决,我认为这是因为根据堆栈溢出建议,“[它]不清楚、范围太广,或者在以回答者可以适当解决的方式确定问题方面存在问题”,我想分享我所做的尝试
- 我遍历了所有范围,并计算出了与其他范围的重叠,但我看不出这一系列新范围对我有什么帮助
- 根据@hon2a的建议,我尝试计算出该范围与其他范围重叠至少3次的范围,但我认为这是我问题的症结所在。我不知道该怎么做
- 从集合中创建3个(或X个)不同范围的所有组合
- 对于每个组合,计算三者的交点
- 返回交点的并集
- 简单的算法是:
//范围:数组,x:number
const combinations=u.combinations(ranges,x)//lodash.combinations
常量交点=combinations.map(combination=>combination.reduce(
(交叉点,范围)=>({
from:Math.max(交点.from,距离.from),
to:Math.min(交点.to,距离.to)
})
{from:Number.MIN\u SAFE\u INTEGER,to:Number.MAX\u SAFE\u INTEGER}
)).filter(({from,to})=>from
我不知道是否可以用较低的时间复杂度来完成,但由于您没有分享任何您实际尝试的信息,我想我应该投票结束,而不是回答任何问题。您所说的“所有持续时间至少重叠X次”是什么意思?是否“至少有X个范围重叠”?第二个代码示例中的第二个“匹配”应该是10:00-10:30,直到13:00。范围总是在小时或X:30开始和结束吗?@hon2a-抱歉,我已经更正了一个输入错误。我还把这个问题的措辞写得好一点。。范围可能在任意时间开始和结束。我对投票结束这个问题感到惊讶,因为我认为这个问题问得很好。也许我误解了在某处提问的要求,需要再次阅读规则。然而,我确实做了你们建议的第一步,但我发现做这一步很困难(至少使用力矩范围)2@cubabit我想是因为不清楚问题出在哪里,所以投票被否决了。我不知道
时刻范围
API看起来是什么样子,但计算范围重叠是微不足道的。如果没有明确说明您尝试了什么以及失败的地方,看起来您只是在使用StackOverflow来完成家庭作业。很有可能这个现象是误导性的,我在答案中添加了一些伪代码。啊,好吧,我可以看到你的观点,但对我来说,这似乎很有趣,因为我不是一个学生,我需要这个来解决专业工作问题。我认为算法不是我的专长,我浪费了一天的时间试图解决这个问题。非常感谢您的帮助。很高兴听到您的帮助很有用:)
// ranges: Array<{ from: number, to: number }>, x: number
const combinations = _.combinations(ranges, x) // lodash.combinations
const intersections = combinations.map(combination => combination.reduce(
(intersection, range) => ({
from: Math.max(intersection.from, range.from),
to: Math.min(intersection.to, range.to)
})
{ from: Number.MIN_SAFE_INTEGER, to: Number.MAX_SAFE_INTEGER }
)).filter(({ from, to }) => from < to)
// ... (union is trivial too)