• 0435无重叠区间 Marathon


    给定一个区间的集合,找到需要移除区间的最小数量,使剩余区间互不重叠。

    注意:

    可以认为区间的终点总是大于它的起点。
    区间 [1,2] 和 [2,3] 的边界相互“接触”,但没有相互重叠。
    示例 1:

    输入: [ [1,2], [2,3], [3,4], [1,3] ]

    输出: 1

    解释: 移除 [1,3] 后,剩下的区间没有重叠。
    示例 2:

    输入: [ [1,2], [1,2], [1,2] ]

    输出: 2

    解释: 你需要移除两个 [1,2] 来使剩下的区间没有重叠。
    示例 3:

    输入: [ [1,2], [2,3] ]

    输出: 0

    解释: 你不需要移除任何区间,因为它们已经是无重叠的了。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/non-overlapping-intervals

    参考:

    python

    # 0435.无重叠区间
    
    class Solution:
        def eraseOverlapingIntervals(self, intervals:[[int]]) -> int:
            """
            贪心算法,右边界排序,从左往右右边界尽量小,记录重叠的数量
            :param intervals:
            :return:
            """
            if len(intervals) == 0: return 0
            intervals.sort(key=lambda x: x[1]) # 按右边界排序
            count = 1 # 非交叉区间shu
            end = intervals[0][1] # 记录区间的分割点, max
            for i in range(1, len(intervals)):
                if end <= intervals[i][0]: # 非交叉区间,前区间的右边界<=当前区间的左边界
                    count += 1
                    end = intervals[i][1]
            return len(intervals) - count # 去掉的重叠区间最少
    
    
    if __name__ == "__main__":
        test = Solution()
        print(test.eraseOverlapingIntervals([ [1,2], [2,3], [3,4], [1,3] ]))
    

    golang

    package greedy
    
    import "sort"
    
    // 贪心算法,右边界升序排序
    func eraseOverlapingIntervals1(intervals [][]int) int {
    	var count int
    	sort.Slice(intervals, func(i, j int) bool {
    		return intervals[i][1] < intervals[j][1]
    	})
    	end := intervals[0][1]
    	for i:=1;i<len(intervals);i++ {
    		if end <= intervals[i][0] { // 非交叉计数
    			count++
    			end = intervals[i][1]
    		}
    	}
    	return len(intervals)-count
    }
    
    
    // 贪心算法-左边界升序排序,比较前区间的右边界与当前区间的左边界
    func eraseOverlapingIntervals(intervals [][]int) int {
    	var flag int
    	sort.Slice(intervals, func(i, j int) bool {
    		return intervals[i][0] < intervals[j][0]
    	})
    	for i:=1;i<len(intervals);i++ {
    		if intervals[i-1][1] > intervals[i][0] {
    			flag++
    			//由于是先排序的,所以,第一位是递增顺序,
    			//故只需要将临近两个元素的第二个值最小值更新到该元素的第二个值即可作之后的判断
    			intervals[i][1] = min(intervals[i-1][1], intervals[i][1])
    		}
    	}
    	return flag
    }
    
    func min(a,b int) int {
    	if a < b {
    		return a
    	}
    	return b
    }
    
  • 相关阅读:
    P1144 最短路计数
    P2966 [USACO09DEC]牛收费路径Cow Toll Paths
    P2419 [USACO08JAN]牛大赛Cow Contest
    P1462 通往奥格瑞玛的道路
    P1346 电车
    P1339 [USACO09OCT]热浪Heat Wave
    P1418 选点问题
    P1330 封锁阳光大学
    P1182 数列分段Section II
    P2661 信息传递
  • 原文地址:https://www.cnblogs.com/davis12/p/15609587.html
Copyright © 2020-2023  润新知