[Leetcode] K Yuan Chu가 선택한 질문의 합계가 포함 된 하위 배열

제목 설명 : 560 sum은 K의 하위 배열입니다.

정수 배열과 정수 k가 주어지면 배열에서 합계가 k 인 연속 하위 배열의 수를 찾아야합니다.

예 1 :

输入:nums = [1,1,1], k = 2
输出: 2 

설명 : [1,1]과 [1,1]은 서로 다른 두 가지 상황입니다.

예 2 :

输入:nums = [1,1,1,0], k = 2
输出: 3 

설명 : [1,1], [1,1], [1,1,0]은 모두

예 3 :

输入:nums = [-1,1,1,0], k = 2
输出: 2

설명 : [1,1], [1,1,0] 모두

주제 요구 사항은 잘 이해되어 있지만 int 유형 배열이기 때문에 발생할 모든 상황을 먼저 고려해야합니다. 따라서 내부의 정수 유형은 0보다 작지 않고 0과 같고 0보다 큽니다. 따라서이 주제를 수행 할 때 배열에 0이 포함 된 상황을 고려해야합니다. 예를 들어, 예제 2에서 [1,1], [1,1,0]은 모두 하위 배열이므로 생략 할 수 없습니다. 사고. 이제 막 문제를 풀기 시작한 학생들 중 일부는 이런 상황을 생각하지 못할 수도 있고, 원래의 문제 예에서는 하나의 예만 주어 졌기 때문에 특별한 상황을 생각할 수없는 경우도 있지만, 붓는 질문의 수가 늘어 나면 문제를 분석하는 능력이 더 좋아질 것입니다. 강해지면 질문을 받으면 먼저 몇 가지 특별한 예를 생각할 수 있습니다.

먼저 폭력적인 해결책에 대해 이야기합시다

참고 : 폭력적인 방법은 쉽게 생각할 수 있지만 폭력적인 방법의 시간 복잡성은 상대적으로 높은 경향이 있습니다. 시간 복잡성은 상대적으로 높지만 폭력적인 해결책을 무시해서는 안됩니다 (특히 모르는 문제가 발생할 때). 대부분의 경우 다른 솔루션은 폭력적인 방법의 최적화이므로 문제를 해결할 때 우월하지 않아야하며 폭력적인 방법을 무시해야합니다. 대신 무차별 대입 방법을 최적화하십시오.

무차별 대입 방법의 아이디어는 매우 간단합니다. 이중 루프, 누적 nums [j], 합계가 K 값이면 카운터가 1 씩 증가합니다. 순회가 끝나면 값이 반환됩니다. 무차별 대입 방법은 0이 존재하는 상황에도 적용 할 수 있습니다. 합계 + 0이므로 값은 여전히 ​​합계이고, 이때 합계가 k와 같으면 카운터는 여전히 1 씩 증가합니다.

여기에 사진 설명 삽입

질문 코드 :

class Solution {
    
    
    public int subarraySum(int[] nums, int k) {
    
    
          if(nums.length == 0){
    
    
              return 0;
          }  
          //计数器
          int count = 0;
          //代表的是蓝指针的运动轨迹
          for(int i =0;i<nums.length;i++){
    
    
              int sum = 0;
              //代表橙指针的运动轨迹
              for(int j =i;j<nums.length;j++){
    
    
                  //将橙指针遍历的值进行相加
                  sum += nums[j];
                  //等于时计数器加1
                  if(sum == k){
    
    
                      count++;
                      //这里不可以break,因为可能有这种情况k=1数组为[1,0,0,1,-1]这个情况
                  }                  
              }
          }
          return count;
    }
}

Hashmap 法 :

이 방법은 좀 더 독창적입니다. Leetcode에는이 방법을 사용할 수있는 몇 가지 질문이 있으므로 독자들이이 방법을 자세히 살펴 보길 바랍니다. 처음 질문을 작성하기 시작하면 조금 어려울 수 있지만 함께 논의 할 수 있습니다.

sum 값의 변화를 살펴 보겠습니다.

sum [0] = nums [0];

sum [1] = nums [0] + nums [1];

sum [2] = nums [0] + nums [1] + nums [2];

sum [3] = nums [0] + nums [1] + nums [2] + nums [3];

sum [3] = sum [2] + nums [3]이므로 sum [3] -sum [2] = nums [3], sum [3] -sum [1] = nums [2] + nums [3 ];

위의 공식을 통해 sum [j] -sum [i] = k이고 변환은 sum [j] -k = sum [i]이며이 문제는 sum [i]의 출현 횟수가됩니다.

여기에 사진 설명 삽입

여기에 사진 설명 삽입

class Solution {
    
           
    public int subarraySum(int[] nums, int k) {
    
    
        int count = 0;//计数器
        if(nums.length < 1){
    
    
            return 0;
        }
        //hashmap用来存sum[i]的和出现的次数
        HashMap<Integer, Integer> map = new HashMap<>();
        map.put(0,1);//防止这种情况,数组只有一个1,k=1则count=1
        int sum = 0;
        for(int i = 0; i<nums.length; i++){
    
    
           sum += nums[i];//累加
            //获取sum-k出现的个数,例当前指针在第j位。sum[j]=10,k=2,
            //则需要知道sum[i]=8时,共有几种情况,sum[i]代表的是前i位的值
           if(map.containsKey(sum - k)){
    
    
               count += map.get(sum-k);//获取次数
           }
           map.put(sum,map.getOrDefault(sum,0)+1);//没出现则存入一次
       }
       return count;
    }
    
}

추천

출처blog.csdn.net/tan45du_yuan/article/details/109297850