leetcode思路6-10

本文详细介绍了四种编程算法:1) Z字形变换,通过遍历和转向实现;2) 整数反转,利用数学除余避免溢出;3) 字符串转整数(atoi),处理正负号和越界;4) 回文数判断,结合整数反转;5) 正则表达式匹配,采用动态规划解决。这些算法涉及字符串处理、数学运算和复杂逻辑,是编程面试中常见的问题。
摘要由CSDN通过智能技术生成

6、Z字形变换

思路:遍历访问

创建一个给定行数大小的列表,存放每行字符。定义一个flag,每到第一行或者最后一行就开始转向,从上到下加,从下到上减,将相应的字符添加到对应行号的字符流中。注意行数小于2的话就直接输出就好,不然会报错。

class Solution {
    public String convert(String s, int numRows) {
        if(numRows<2){
            return s;
        }
        List<StringBuffer> list=new ArrayList<>();
        for(int i=0;i<numRows;i++){
            list.add(new StringBuffer());
        }
        int i=0,flag=-1;
        for(char c:s.toCharArray()){
            list.get(i).append(c);
            if(i==0||i==numRows-1){
                flag=-flag;
            }
            i+=flag;
        }
        StringBuffer res=new StringBuffer();
        for(StringBuffer sb:list){
            res.append(sb);
        }
        return res.toString();
    }
}

7、整数反转

思路:数学除余

利用数学的话,就要考虑溢出的问题。Java里遇到溢出时不会报错,但会导致数字发生变化。我们可以利用最终得到的数字/10看是否等于前一阶段的数字来判断是否溢出。当然也可以用字符反转的方式。

class Solution {
    public int reverse(int x) {
        int res=0;
        int temp=0;
        while(x!=0){
            temp=res;
            res=(res*10)+(x%10);
            x/=10;
        }
        if(temp!=res/10){
            return 0;
        }
        return res; 
    }
}

8、字符串转换整数(atoi)

思路:比较判断

整体步骤:1)去掉前导空格;2)处理正负号;3)识别数字,并考虑是否越界。

class Solution {
    public int myAtoi(String s) {
        char[] chars=s.toCharArray();
        int n=s.length();
        int idx=0;
        //去掉空格
        while(idx<n&&chars[idx]==' '){
            idx++;
        }
        //看去掉空格之后是否为空
        if(idx==n){
            return 0;
        }
        boolean flag=false;
        //判断数字前是否有正负号,有负号的话flag=true
        if(chars[idx]=='-'){
            flag=true;
            idx++;
        }else if(chars[idx]=='+'){
            idx++;
        }else if(!isDigit(chars[idx])){
            return 0;
        }
        int ans=0;
        //未出边界且始终为数值
        while(idx<n&&isDigit(chars[idx])){
            int digit=chars[idx]-'0';
            //注意这里,是ans*10+digit>Integer.MAX_VALUE的变形
            if(ans>(Integer.MAX_VALUE-digit)/10){
                return flag?Integer.MIN_VALUE:Integer.MAX_VALUE;
            }
            ans=ans*10+digit;
            idx++;
        }
        return flag?-ans:ans;
    }
    //判断一个字符是否是数字
    private boolean isDigit(char c){
        if(c>='0'&&c<='9'){
            return true;
        }
        return false;
    }
}
#

9、回文数

思路:整数反转

利用第7题中的整数反转,判断反转前后是否相当。溢出或者是负数肯定不是回文数。

class Solution {
    public boolean isPalindrome(int x) {
    	//负数直接返回false
        if(x<0){
            return false;
        }
        //记录反转后的数字
        int res=0;
        //x的副本
        int temp=x;
        while(temp!=0){
            res=res*10+(temp%10);
            temp/=10;
        }
        return res==x;
    }
}

10、正则表达式匹配

思路:动态规划

比较枯燥的一道题,需要考虑各种情况。假设字符串s、正则表达式为p,dp[i][j]表示字符串前i位与正则表达式前j位是否达成匹配关系。总的来说分三种情况:

  • p[i] == s[i] : dp[i][j] = dp[i-1][j-1]
  • p[j] == ‘.’ : dp[i][j] = dp[i-1][j-1]
  • p[j] == ‘*’ :
    p[j-1] != s[i]&&p[j-1] != ‘*’ : dp[i][j]=dp[i][j-2]
    p[j-1] == s[i] || p[j-1] == ‘.’ : dp[i][j] = dp[i-1][j] ||dp[i][j-2]
class Solution {
    public boolean isMatch(String A, String B) {
        int n = A.length();
        int m = B.length();
        boolean[][] f = new boolean[n + 1][m + 1];

        for (int i = 0; i <= n; i++) {
            for (int j = 0; j <= m; j++) {
                //懒得再写个循环赋值了,其实就是f[0][0]=true,其他都是false
                if (j == 0) {
                    f[i][j] = i == 0;
                } else {
                    //非空正则分为两种情况 * 和 非*
                    if (B.charAt(j - 1) != '*') {
                    	//前两种情况
                        if (i > 0 && (A.charAt(i - 1) == B.charAt(j - 1) || B.charAt(j - 1) == '.')) {
                            f[i][j] = f[i - 1][j - 1];
                        }
                    } else {
                        //碰到 * 了,分为看和不看两种情况
                        //不看,也就是第三种情况的第一个
                        if (j >= 2) {
                            f[i][j] |= f[i][j - 2];
                        }
                        //看,理解为对上一个if的补充
                        if (i >= 1 && j >= 2 && (A.charAt(i - 1) == B.charAt(j - 2) || B.charAt(j - 2) == '.')) {
                            f[i][j] |= f[i - 1][j];
                        }
                    }
                }
            }
        }
        return f[n][m];
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值