1. 程式人生 > >無序陣列中找到最長連續子序列

無序陣列中找到最長連續子序列

原始題目:

給定一個無序的整數序列, 找到最長的連續子序列。

例如:

給定[100, 4, 200, 1, 3, 2],

最長的連續子序列是[1, 2, 3, 4]。

第一種解法:不要求時間複雜度,直接排序後比較得到最長子序列。

第二種解法:要求時間複雜度,用HashSet的空間換時間。先將元素全部放入HashSet中,然後從第一個元素開始,取出,找x-1是否在set裡, 若在 就 跳出,判斷下一個元素(因為若x-1在set中,我們從當前的元素開始尋找連續子序列是無意義的,因為找到的子序列也不會是最長的,我們必須 從 當前元素的上一個元素不在set中開始向後尋找子序列),不在就找x+1,x+2...是否在set裡,直到x+i不在set中,算出子序列長度,與最長的進行比較。


import java.util.HashSet;

/** 
 * Longest Consecutive Sequence 
 *  
 * Given an unsorted array of integers, find the length of the longest 
 * consecutive elements sequence. 
 *  
 * For eample, Given [100, 4, 200, 1, 3, 2], The longest consecutive elements 
 * sequence is [1, 2, 3, 4]. Return its length: 4. 
 *  
 * Your algorithm should run in O(n) complexity. 
 *  
 */  
public class LongestConsecutiveSequence {
	public static void main(String args[]){
		int arr[]={100,4,200,1,3,2};
		System.out.println(find2(arr));
//		for(int i=0;i<arr.length;i++)
//		System.out.println(arr[i]);
	}
	/*如果不要求o(n)時間複雜度 直接排序後比較得到最長子序列*/
	public static int find1(int arr[]){
		sort(arr,0,arr.length-1);
		int max=1;
		int temp=1;
		for(int i=0;i<arr.length-1;i++){
			if(arr[i+1]==arr[i]+1){
                 temp++;
                 System.out.println(temp+"aa");
			}
			else{
				max=Math.max(max, temp);
				temp=1;
			}			
		}
		max=Math.max(max, temp);
		return max;
	}	 
	/*快排*/
	public static void sort(int arr[],int left,int right){
		if(left<right){
		int mid=partition(arr,left,right);
		sort(arr,left,mid-1);
		sort(arr,mid+1,right);
		} 
	}
	public static int partition(int arr[],int left,int right){
		int pointKey=arr[left];
		while(left<right){
		 while(arr[right]>pointKey&&left<right){
			 right--;
		 }	
		 arr[left]=arr[right];
		 while(arr[left]<pointKey&&left<right){
			 left++;
		 }
		 arr[right]=arr[left];
		}
		 arr[left]=pointKey; 
		 return left;
		
	}
	/*要求在o(n)時間複雜度  用hashSet 空間換時間*/
	public static int find2(int []arr){
		HashSet<Integer> set=new HashSet<>();
		int max=1;
		for(int array:arr){
			set.add(array);
		}
		for(int array:arr){
			if(set.contains(array-1)){//array-1在set裡面,直接跳出,開始下一次遍歷
				continue;
			}
			else {
				int temp=array;
			  while(set.contains(temp)){
				  set.remove(temp);//找到一個就從set中移除一個,這樣後續的set在查詢時效率會提高
				  temp++;
			  }
			//	while(set.remove(temp++));//加分號表示沒有迴圈語句
			  if(temp!=array){
			  max=Math.max(max, temp-array);
			  System.out.println("max"+max);
			  }
			}
		}
		return max;
		
	}
}