两个线段区间A、B 求他们的交集

 

package com.java.ly2011.October;

import java.util.ArrayList;
import java.util.List;


/**
 *
 *  a 区间0,3 1,6 10,20
 *  b 区间0,1 20,50 4,5
 *
 * 找出ab重叠的区间   ab内部本身也存在重叠的可能
 *
 * 1 ab区间序列分别按x,y中的x值 各自内部排序
 * 2 各自内部合并重复区间(从前道后遍历一遍即可)
 * 3 两个区间求重叠部分(两个下标 ,分别指向a、b 同时遍历求的交集)
 * @author ly
 *
 */
public class OverlapLine {
 
 public static void main(String[] args) {
  int[][]  a = new int[][]{
    new int[]{0,3},
    new int[]{1,6},
    new int[]{10,20}
  };
  int[][]  b = new int[][]{
    new int[]{0,1},
    new int[]{20,50},
    new int[]{4,5}
  };
  
/*  sortArray(a);
  sortArray(b);
  a = unionLine(a);
  b = unionLine(b);
  List<int[]> list = findOverLap(a, b);
  int count = countLength(list);*/
  
  
  int count = findOverLapLength(a, b);
  System.out.println(count);
 }
 
 /**
  * 插入排序
  * @param a
  */
 public static void sortArray(int[][] a){
  
  for(int i=1 ; i<a.length;i++){
   int[] key = a[i];
   int j;
   for(j=i-1;j>=0;j--){
    if(a[j][0]>key[0]){
     a[j+1]= a[j];
    }
    else
     break;
   }
   a[j+1]= key;
  } 
 }
 
  /**
   * 内部合并
   * @param a
   * @return
   */
  public static int[][] unionLine(int[][] a){
  
    int shift = 0;
    for(int i= 1 ;i<a.length;i++){
    if(shift>0)
     a[i-shift]=a[i];
       if(a[i-shift-1][1]>=a[i-shift][0]){
        int maxy = a[i-shift-1][1]>a[i-shift][1]?a[i-shift-1][1]:a[i-shift][1];
        a[i-shift-1] = new int[]{a[i-shift-1][0],maxy};
        shift++;
       }
    }
   int[][] result = new int[a.length-shift][];
   for(int i = 0;i<result.length;i++){
    result[i]=a[i];
   }
  
   return result;
  }
 
 /**
  * 求交集
  * @param a
  * @param b
  * @return
  */
 public static List<int[]> findOverLap(int[][] a , int[][] b){
  List<int[]> list = new ArrayList<int[]>();
  int i =0;
  int j =0;
  
  while(i<a.length&&j<b.length){
   
   int maxX = a[i][0]>b[j][0]?a[i][0]:b[j][0];
   int minY = a[i][1]<b[j][1]?a[i][1]:b[j][1];
   
   if(maxX<minY){
    int[] temp = new int[]{maxX,minY};
    list.add(temp);
   }
   if(a[i][1]<b[j][1])
    i++;
   else
    j++;
  }
  
  return list;
 }
 
 /**
  *  算长度
  * @param list
  * @return
  */
 public static int countLength(List<int[]> list){
  int sum =0;
  for(int i =0 ;i<list.size();i++){
   int[] temp = list.get(i);
   sum+= (temp[1]-temp[0]);
  }
  return sum; 
 }
 
 
 public static int findOverLapLength(int[][] a , int[][] b){
  sortArray(a);
  sortArray(b);
  a = unionLine(a);
  b = unionLine(b);
  List<int[]> list = findOverLap(a, b);
  int count = countLength(list);
  return count;
 }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值