Leetcode 브러시 제목 --N-합 문제를 지적

2Sum;

주제 설명 :

조건 A, B를 만족시키는 하나 개의 어레이를 가정하고 상기 nums 주어진 정수 배열 타겟은, 어레이로부터되도록 + B = B A 대상을 찾아

독창적 인 아이디어 :

결과를 찾기 위해 배열을위한 두 개의 루프는 시간 복잡도는 O (N- 2 )

최적화 아이디어 :

해시 테이블을 사용하여 HashMap에 <정수 정수>지도, 키 - 값 쌍 확립 <nums [I]를 I>. 각 카운트 nums [I]의 배열 nums 통해, 기록 목표 nums [I]와 동일한 키가있는 경우이며, 만약 그렇다면, 쿼리 해시 테이블을 검색하고, 그렇지 않으면, NUM [I] 첨자 I 저장된 해시 테이블. 해쉬 테이블 조회 시간 복잡도는 O으로 간주 할 수 있기 때문에 (1), 그래서 알고리즘의 시간 복잡도는 (n)은 O로 감소된다.

 

3Sum :

주제 설명 :

어레이에서 [C, A, B] 모두 구별을 찾기 위해 정수의 어레이 nums 주어진 예 + B + C = O 그

독창적 인 아이디어 :

순환 3,하지만 초과 근무

최적화 아이디어 :

더블 포인터. 우선, (중복을 방지하기 위해), 각각의 위치 I에서의 어레이를 가로 질러 배열을 정렬, 두 포인터는 위치 I + 1이고, 위치의 오른쪽 포인터가 가리키는 왼쪽 포인터 지점을 제공 nums.length-1, 및 경우 3 개소의 합계를 산출 0과 동일하고 표준 가산 결과 집합의 수가 3 위치, 왼쪽 및 오른쪽, 왼쪽, 오른쪽, 0보다 클 경우, 그 좌우 포인터 미만 0 후 왼쪽과 오른쪽 손 좌우 포인터 경우 만나기 전까지. 끝으로 반복은 [C, A, B] 모든 자격을 찾을 수 있습니다. 따라서 중복을 방지하기 위해, 포인터가 상부와 동일한 수의 위치로 이동하면, 하부 위치의 수는 하나의 이동을 계속. 이 방법은 시간 복잡도 (N- O 제어 될 수있다 2 ).

 

3SumClosest :

주제 설명 :

nums 정수 배열 타겟 및 배열에서 식별 번호 3의 합이 주어 지도록 최소 타겟 사이의 차이의 절대 값의 합

아이디어 :

그리고 3Sum 마찬가지로, 이중 포인터의 사용.

 

4Sum;

주제 설명 :

nums 주어진 정수 어레이, 타겟 어레이의 모든 어레이 급 [A, B, C, D]를 찾기 위해 반복되지 않을 것이다 그러한 + B + C + D = 목표 그

아이디어 :

3Sum 4Sum로 분해하는 분해 후 2Sum, 2Sum 해시 맵으로 세분화 또는 이중 포인터 O 시간 복잡성 (N- 제어하는데 사용될 수있다 . 3 ). 실제 코드 구현은 중복을 피하기 위해, 상기 판정 조건의 일부 이용할 수있다 (예를 : 배열이 오름차순이기 때문에, 전류 nums는 [내가] * 4> 타겟팅하는 경우 , 브레이크 직접 가능) 속도 최적화.

특정 구현 :

목록 공개 <일람 <정수 >> fourSum (INT [상기 nums, INT 타겟) { 
일람 <일람 <정수 >> 새로운 새 RES = ArrayList를은 <> ();
// 어레이는 4 이하, 리턴 빈 또는 길이이다
= 경우 (nums을 널 nums.length || = <. 4)
복귀 RES;
// 정렬
; Arrays.sort에합니다 (nums)
// 배열이 너무 크거나 너무 작은 배열 반환
(nums [0] * 4 경우 타겟 || nums [nums>. . (1) 길이] * 4 <목표) 반환 RES가,.

위해 (I = 0 나타내는 int. I를 <-nums.length 3] I는 ++) {
// 판정 조건 nums 않음을 유의 [I + 1] == nums [I] 결과의 하나의 세트가 중복 될 수 있으므로 수는
경우 (I = 0 && nums [ I-1] == nums [I]!) 계속 // 중복을 피하기 위해

IF합니다 (nums [I] == * 목표 4.) {
IF 합니다 (nums가 [I가 +3.] == nums [I]) {
res.add (Arrays.asList합니다 (nums [I] 상기 nums [I] 상기 nums [I] 상기 nums [I]));
RES를 리턴;
}
}

경우 (nums [I] + 3 *의 nums [nums.length-1] <타겟) 계속; // nums [I]太小

경우 (nums [I] * 4> 타깃) 창 입술; // nums [I]太大

threeSumForFourSum (nums, 타겟 nums [I], I + 1, 입술, nums [I]);
}
고해상도를 반환;

}

공개 무효 threeSumForFourSum (INT [] nums, INT 대상, INT 시작 일람 <일람 <정수 >> 입술, INT의 Z1)는 {

(3 *의 nums는 [시작] 경우> || 3 *의 nums [nums.length 1 타겟팅 ] <타깃) 창;

대 (INT I = 시작; 나는 <; 내가 ++ nums.length-2) {

경우 (nums [I]가 3 *> 타깃) 창; //过大

경우 (nums [I] + nums [nums.length-1] * 2 <목표) 계속; //过小

(I = && nums 시작 [I-1] == nums [I]!) 경우 계속;


경우 (nums [I + 2] == nums [I]) {
res.add (Arrays.asList (Z1, nums [I] nums [I] nums [I]));
반환;
}
}
twoSumForFourSum (nums, 타겟 nums [I], I + 1, 입술, Z1, nums [I]);
}

}

공개 무효 twoSumForFourSum (INT [] nums, INT 대상, INT 시작 일람 <일람 <정수 >> 입술, INT Z1, Z2 INT) {

창 (nums.length == 1 시작) 경우;

만약 수익 (nums *이 2> 타겟 [시작])를;

HashMap에 <정수 정수> = 새로운 맵의 HashMap <> ();
대 (INT I = 시작; 나는 nums.length를 <; 내가 ++) {
(! 난 = && nums 시작 [I-1] == nums [I])를 계속하는 경우; //避免重复
경우 (I! = nums.length 1 && 2 * nums [I] == 타겟) {
경우 (nums [I + 1] == nums [I]) {
res.add (Arrays.asList (Z1, Z2, nums [I] nums [I]));
}
}
INT 컷 = 타겟 nums [I];
경우 (map.containsKey (절단)) {
res.add (Arrays.asList (Z1, Z2, 컷 nums [I]));
잇다;
}
map.put (nums [I], I);
}
}

 

추천

출처www.cnblogs.com/yingying7/p/11044215.html