数字与字符串间转换 299、412、506、539、553、537、592、640

299. 猜数字游戏

解法一、遍历+计数

如果是公牛数,A++,剩余的部分都一定是位置不对的。如果是奶牛数,取a计数和b计数里较小的数字、即两字符串出现频数的重叠部分即可

class Solution {
    public String getHint(String secret, String guess) {
        int A = 0;
        int B = 0;
        int[] a = new int[10];
        int[] b = new int[10];
        int len = secret.length();
        for(int i = 0;i< len;i++){
            if(secret.charAt(i) == guess.charAt(i)){
                A++;
            }else{
                a[secret.charAt(i) - '0']++;
                b[guess.charAt(i)-'0']++;
            }
        }
        for(int i = 0;i<=9;i++){
            B+= Math.min(a[i],b[i]);
        }
        return A+"A"+B+"B";
    }
}

412. Fizz Buzz

方法一、遍历,分情况讨论

class Solution {
    public List<String> fizzBuzz(int n) {
        List<String> Arr=new ArrayList<>();
        for(int i=1;i<=n;i++){
            if(i%3==0 && i % 5 == 0){
                Arr.add("FizzBuzz");
            }else if(i%3==0){
                Arr.add("Fizz");
            }else if(i%5==0){
                Arr.add("Buzz");
            }else{
                Arr.add(String.valueOf(i));
            }
        }
        return Arr;
    }
}

506. 相对名次

解法一、排序再标记

 其实我用了哈希表。但这个不需要精确查取,数组已经够了

class Solution {
    public String[] findRelativeRanks(int[] score) {
        int n = score.length;
        String[] desc = {"Gold Medal", "Silver Medal", "Bronze Medal"};
        int[][] arr = new int[n][2];

        for (int i = 0; i < n; ++i) {//存入
            arr[i][0] = score[i];
            arr[i][1] = i;
        }
        Arrays.sort(arr, (a, b) -> b[0] - a[0]);//排序
        String[] ans = new String[n];//答案
        for (int i = 0; i < n; ++i) {
            if (i >= 3) {
                ans[arr[i][1]] = Integer.toString(i + 1);
            } else {
                ans[arr[i][1]] = desc[i];
            }
        }
        return ans;
    }
}

作者:力扣官方题解
链接:https://leetcode.cn/problems/relative-ranks/solutions/1131693/xiang-dui-ming-ci-by-leetcode-solution-5sua/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

539. 最小时间差

解法一、转换单位、排序再比较

字符串无法比对,所以先转换成数字,然后求排序后数组最小值。因为时间是个环,需要考虑一下结尾(1440是59*60+59+1)

如果长度>1440,一定有两个数字重合,则直接返回0(这是3ms→2ms的关键

说起来Collections类居然可以排字符串

class Solution {
    public static int findMinDifference(List<String> timePoints) {
        int len = timePoints.size();
        int[] a = new int[len];
        int min = Integer.MAX_VALUE;
        if (len > 1440) {
            return 0;
        }
        for(int i = 0;i<len;i++){
            String time =  timePoints.get(i);
            a[i] = ((time.charAt(0)-'0')*10 + (time.charAt(1) - '0'))*60 + ((time.charAt(3)-'0')*10 + (time.charAt(4) - '0'));
        }
        Arrays.sort(a);
        for(int i = 1;i < len;i++){
            int t = [a[i] - a[i-1];
            min = Math.min(min,t);
        }
        int t = (a[0] - a[len-1] + 1440) % 1440;
        min = Math.min(min,t);
        return min;
    }
}

 

553. 最优除法

 

解法一、字符串处理+脑筋急转弯

其实就是在第一个数后面直到最后都括起来,如{1,2,3,4,5,6}就是1/(2/3/4/5/6),本质上是字符串题

不难,因时间大受打击

class Solution {
    public static String optimalDivision(int[] nums) {
        int len = nums.length;
        StringBuffer sb = new StringBuffer();
        if(len == 1){
            return String.valueOf(nums[0]);
        }
        sb.append(String.valueOf(nums[0])+"/(");
        for(int i = 1;i < len-1;i++){
            sb.append(String.valueOf(nums[i])+'/');
        }
        sb.append(String.valueOf(nums[len-1])+')');
        return sb.toString();
    }
}

 

优化后如下,原来不需要String.valueOf,而且也最好不要用字符串拼接(不过为什么,是很花时间吗

class Solution {
    public static String optimalDivision(int[] nums) {
        int len = nums.length;
        StringBuffer sb = new StringBuffer();
        if (len == 1) {
            return sb.append(nums[0]).toString();
        }
        if (len == 2) {
            return sb.append(nums[0]).append("/").append(nums[1]).toString();
        }
        sb.append(nums[0]).append("/(");
        for(int i = 1;i < len-1;i++){
            sb.append(nums[i]).append('/');
        }
        sb.append(nums[len-1]).append(')');
        return sb.toString();
    }
}

537. 复数乘法

解法一、转换,处理,直接求

因为num1和num2都是r+i的形式,找到加号,往前处理;往后处理(记得不要算i,所以是len-1)

当然后来发现比起valueOf,parseInt更好

官方用了正则

String[] complex1 = num1.split("\\+|i");
class Solution {
    public String complexNumberMultiply(String num1, String num2) {
        int r = 0;
        int i = 0;
        int indexA = num1.indexOf('+');
        int rA = Integer.valueOf(num1.substring(0,indexA));
        int iA = Integer.valueOf(num1.substring(indexA+1,num1.length()-1));
        int indexB = num2.indexOf('+');
        int rB = Integer.valueOf(num2.substring(0,indexB));
        int iB = Integer.valueOf(num2.substring(indexB+1,num2.length()-1));
        r = rA * rB - iA*iB;
        i = rA * iB + rB * iA;
        StringBuffer sb = new StringBuffer();
        return  sb.append(r).append('+').append(i).append('i').toString();
    }
}

592. 分数加减运算

解法一、先转数字再运算

见注释!

class Solution {
    public static String fractionAddition(String expression) {
        int len = expression.length();
        int num = 0;
        for(int i = 0;i < len;i++){//计算一共有多少个分数,存作num
            if(expression.charAt(i) == '/')num++;
        }
        int[][] a = new int[num][2];
        if(num == 1){
            return expression;
        }
        String[] fractions = expression.split("(?=[-+])");//正则分割开
        int temp = 1;
        for(int i = 0;i < num;i++){//0存分子,1存分母
            int index = fractions[i].indexOf('/');
            a[i][0] = Integer.parseInt(fractions[i].substring(0,index));
            a[i][1] = Integer.parseInt(fractions[i].substring(index+1));
            temp*= a[i][1];//分母的累乘
        }
        int sum = 0;
        for(int i = 0;i < num;i++){//sum+=分子*相差倍数
            sum+= a[i][0] * (temp/a[i][1]);
        }
        int t = Math.abs(gcd(sum,temp));//最大公约数
        sum/=t;//处理分子与分母
        temp/=t;
        StringBuffer sb = new StringBuffer();
        sb.append(sum).append('/').append(temp);
        return sb.toString();

    }
    public static int gcd(int a, int b) {
        if (b == 0) {
            return a;
        }
        return gcd(b, a % b);
    }
}

 

640. 求解方程

 

解法一、模拟

太难了没敲出来。。有点复杂。循环遍历原字符串转为数字,'+'‘-’的时候变符号,x是x系数,num是常数,‘=’的时候翻转模拟变号。最后讨论。

class Solution {
    public String solveEquation(String s) {
        int x = 0, num = 0, n = s.length();
        char[] cs = s.toCharArray();
        for (int i = 0, op = 1; i < n; ) {
            if (cs[i] == '+') {
                op = 1; i++;
            } else if (cs[i] == '-') {
                op = -1; i++;
            } else if (cs[i] == '=') {
                x *= -1; num *= -1; op = 1; i++;
            } else {
                int j = i;
                while (j < n && cs[j] != '+' && cs[j] != '-' && cs[j] != '=') j++;
                if (cs[j - 1] == 'x') x += (i < j - 1 ? Integer.parseInt(s.substring(i, j - 1)) : 1) * op;
                else num += Integer.parseInt(s.substring(i, j)) * op;
                i = j;
            }
        }
        if (x == 0) return num == 0 ? "Infinite solutions" : "No solution";    
        else return "x=" + (num / -x);
    }
}

作者:宫水三叶
链接:https://leetcode.cn/problems/solve-the-equation/solutions/1736347/by-ac_oier-fvee/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

38. 外观数列

解法一、模拟遍历

class Solution {
    public static String countAndSay(int n) {
        return RLE("1",n);
    }
    public static String RLE(String a,int num){
        if(num==1)return a;
        int len = a.length();
        StringBuffer sb = new StringBuffer();
        int ptr = 0;
        while(ptr<len){
            int count = 1;
            while (ptr<len-1 && a.charAt(ptr) == a.charAt(ptr+1)){
                ptr++;//统计数量用
                count++;
            }
            sb.append(count);
            sb.append(a.charAt(ptr));
            ptr++;
        }
        return RLE(sb.toString(),--num);
    }
}

 

感觉这么写更正统一些

class Solution {
    public String countAndSay(int n) {
        if (n == 1) {
            return "1";
        }
        String s = countAndSay(n - 1);
        StringBuilder sb = new StringBuilder();
        for (int i = 0; i < s.length();) {
            char c = s.charAt(i);
            int count = 0;
            while (i < s.length() && s.charAt(i) == c) {
                count++;
                i++;
            }
            sb.append(count).append(c);
        }
        return sb.toString();
    }
}

解法二、打表

不必多说jpg 

 


 

碎碎念

  • 学会了降序数组的比较器写法 Arrays.sort(arr, (a, b) -> b[0] - a[0]);
  • 对于539,强调了len最开始可以滤掉一部分特殊情况,对优化时间来说很重要
  • 熟悉了while+ptr遍历字符串转换的流程,对0和len-1的了解也纯熟很多
  • 写秃了 640是真复杂啊 兄弟
  • ↓是Collections类
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值