周赛326总结

简介: 优化:不需要判断i是否是质因数,因为num已经用前面的i 分解了,所以从小到大用i 能够整除num时,i一定是num的质因数

周赛326总结


感谢力扣,第一次全部做完,耗时43分37秒,很满足了,虽然是题比较简单,新的一年继续努力呀!!


计能整除数字的位数


Given an integer num, return the number of digits in num that divide num.


An integer val divides nums if nums % val == 0.


  • 思路:通过整除和取余的运算将num的每个数位取出,判断是否能整除num,统计能够整除的数位个数返回即可


  • 实现


class Solution {
    public int countDigits(int num) {
        int ans = 0;
        int cur = num;
        while(cur / 10 != 0){
            int x = cur % 10;
            if (num % x == 0){
                ans++;
            }
            cur /= 10;
        }
        if (num % cur == 0){
            ans++;
        }
        return ans;
    }
}


。复杂度


  • 时间复杂度:O ( n ) ,n 为num的数位个数
  • 空间复杂度:O ( 1 )


  • 别人的代码就是好看


// arignote
class Solution {
  public int countDigits(int num) {
    int count = 0;
    for (int i = num; i > 0; i /= 10) {
      count += num % (i % 10) > 0 ? 0 : 1;
    }
    return count;
  }
}


数组乘积中的不同质因数数目


Given an array of positive integers nums, return the number of distinct prime factors in the product of the elements of nums.


Note that:


  • A number greater than 1 is called prime if it is divisible by only 1 and itself.
  • An integer val1 is a factor of another integer val2 if val2 / val1 is an integer.


  • 思路:求出数组nums中每个数的质因数,并存储在set集合中,最终返回set集合的大小


  • 实现


class Solution {
    public int distinctPrimeFactors(int[] nums) {
        Set<Integer> set = new HashSet<>();
        for (int num : nums){
            for (int i = 2; i <= num; i++){
                while (num >= i && num % i == 0 && isPrime(i)){
                    set.add(i);
                    num /= i;    
                }
            }            
        }
        return set.size();
    }
    public boolean isPrime (int x){
        if (x <= 1){
            return false;
        }
        for (int i = 2; i * i <= x; i++){
            if (x % i == 0){
                return false;
            }
        }
        return true;
    }
}


。复杂度


  • 时间复杂度:O(nU),n为nums的长度,U=max(nums)
  • 空间复杂度:O ( U /l o g U ) ,最多有U/ l o g U  个质因数


  • 优化:不需要判断i是否是质因数,因为num已经用前面的i 分解了,所以从小到大用i 能够整除num时,i一定是num的质因数


class Solution {
    public int distinctPrimeFactors(int[] nums) {
        Set<Integer> set = new HashSet<>();
        for (int num : nums){
            for (int i = 2; i <= num; i++){
                while (num >= i && num % i == 0){
                    set.add(i);
                    num /= i;    
                }
            }            
        }
        return set.size();
    }
}


。复杂度


  • 时间复杂度:image.png,n 为nums的长度,U=max(nums)
  • 空间复杂度:O ( U /l o g U ) ,最多有U /l o g U个质因数


将字符串分割成值不超过 K 的子字符串


You are given a string s consisting of digits from 1 to 9 and an integer k.


A partition of a string s is called good if:


  • Each digit of s is part of exactly one substring.
  • The value of each substring is less than or equal to k.


Return the minimum number of substrings in a good partition of s. If no good partition of s exists, return -1.


Note that:


  • The value of a string is its result when interpreted as an integer. For example, the value of "123" is 123 and the value of "1" is 1.


  • A substring is a contiguous sequence of characters within a string.


  • 思路:贪心划分子字符串,保证每个子字符串的长度为所能够到达的最大长度,假设k的位数为n,子字符串的左边界为l ll,如果s.substring(l, l+n)对应的整数大小小于等于k,那么该子字符串即为最优子字符串;反之,s.substring(l, l+n - 1)为最优子字符串


。局部最优:每个子字符串的长度为最大长度

。全局最优:子字符串个数最少


  • 实现


注意右边界的处理和k kk小于10的处理


。保证右边界小于等于字符串长度,如果右边界超出字符串长度,那么直接取最大值

。如果k小于10时,可能出现不能划分好字符串的情况,即字符串中的单个数值大于k时,此时返回-1


class Solution {
    public int minimumPartition(String s, int k) {
        int n = 1;
        int temp = k;
        while (temp / 10 > 0){
            temp /= 10;
            n++;
        }
        int l = 0, m = s.length(), ans = 0;
        while (l < m){
            int r = l + n <= m ? l + n : m;
            if (Integer.parseInt(s.substring(l,r)) <= k){
                l += n;
                ans++;
            }else if(n == 1){
                return -1;                
            }else{
                l += n - 1;
                ans++;
            }
        }
        return ans;
    }
}


。复杂度


  • 时间复杂度:O(m+logk),n 为k的数位数量,m 为s的长度
  • 空间复杂度:O ( 1 )


  • 在遍历的过程中计算子字符串的整数值,不使用Integer.parseInt


// arignote
class Solution {
  public int minimumPartition(String s, int k) {
    int count = 0;
    for (int i = 0; i < s.length(); count++) {
      if (s.charAt(i) - '0' > k) {
        return -1;
      }
      for (long curr = 0; i < s.length() && (curr = curr * 10 + s.charAt(i) - '0') <= k; i++) {
      }
    }
    return count;
  }
}


。复杂度


  • 时间复杂度:O(m),n 为k的数位数量,m 为s的长度
  • 空间复杂度:O ( 1 )


范围内最接近的两个质数


Given two positive integers left and right, find the two integers num1 and num2 such that:


  • left <= nums1 < nums2 <= right .
  • nums1 and nums2 are both prime numbers.
  • nums2 - nums1 is the minimum amongst all other pairs satisfying the above conditions.


Return the positive integer array ans = [nums1, nums2]. If there are multiple pairs satisfying these conditions, return the one with the minimum nums1 value or [-1, -1] if such numbers do not exist.


A number greater than 1 is called prime if it is only divisible by 1 and itself.


  • 思路:求出区间[left,right]范围的所有质数,并使用变量pre记录前一个质数的大小,dis记录最小质数距离,如果当前质数与前一个质数的距离小于当前最小距离,那么更新结果集。


  • 实现


class Solution {
    public int[] closestPrimes(int left, int right) {
        int[] res = {-1, -1};
        int pre = -1;
        int dis = Integer.MAX_VALUE;
        for (int i = left; i <= right; i++){
            if (isPrime(i)){
                if (pre != -1 && i - pre < dis){
                    dis = i - pre;
                    res[0] = pre;
                    res[1] = i;
                }
                pre = i;
            }
        }
        return res;
    }
    public boolean isPrime(int x){
        if (x == 1){
            return false;
        }
        for (int i = 2; i * i <= x; i++){
            if (x % i == 0){
                return false;
            }
        }
        return true;
    }
}


。复杂度


  • 时间复杂度:O(nlogn)
  • 空间复杂度:O ( 1 )


  • 优化:避免重复判断一个数是否是质数,可以提前打表,由于整数范围为[2,100000],可以将该范围内的数进行预处理,然后找到[left,right]范围内的质数,找到相邻的距离最小的两个质数进行返回


// arignote
class Solution {
  private static ArrayList<Integer> list = new ArrayList<>() {
    {
      Boolean[] prime = new Boolean[1000000];
      for (int i = 2; i < 1000000; i++) {
        if (prime[i] == null) {
          add(i);
          for (int j = 2 * i; j < 1000000; j += i) {
            prime[j] = false;
          }
        }
      }
    }
  };
  public int[] closestPrimes(int left, int right) {
    int[] result = { -1, -1 };
    for (int i = 1; i < list.size(); i++) {
      if (list.get(i - 1) >= left && list.get(i) <= right
          && (result[0] < 0 || list.get(i) - list.get(i - 1) < result[1] - result[0])) {
        result = new int[] { list.get(i - 1), list.get(i) };
      }
    }
    return result;
  }
}


目录
相关文章
|
5月前
【周赛总结】周赛354
【周赛总结】周赛354
47 0
|
5月前
13-周赛347总结
13-周赛347总结
50 0
|
5月前
14-周赛348总结
14-周赛348总结
49 0
|
5月前
|
人工智能 BI
12-周赛338总结
12-周赛338总结
49 0
|
5月前
|
存储
10-周赛336总结
10-周赛336总结
56 0
|
5月前
9-周赛335总结
9-周赛335总结
48 0
|
5月前
|
算法 Windows
【周赛总结】周赛360
【周赛总结】周赛360
46 0
|
5月前
【周赛总结】周赛356
【周赛总结】周赛356
54 0
|
5月前
【周赛总结】18-周赛353
【周赛总结】18-周赛353
57 0
|
5月前
|
算法
8-周赛334总结
8-周赛334总结
47 0