代码随想录算法训练营第二十八天|93.复原IP地址、78.子集、90.子集II

93.复原IP地址

public class Solution {
    List<string> result=new List<string>();
    public IList<string> RestoreIpAddresses(string s) {
        if(s.Length>12)
        {
            return result;
        }
        backtracking(s,0,0);
        return result;
    }
    public void backtracking(string s,int startIndex,int pointsum)
    {
        if(pointsum==3)
        {
            if(Isvalid(s,startIndex,s.Length-1))
            {
                result.Add(s);
            }
               return;
        }
        for(int i=startIndex;i<s.Length;i++)
        {
            if(Isvalid(s,startIndex,i))
            {
                s=s.Substring(0,i+1)+"."+s.Substring(i+1);
                pointsum++;
                backtracking(s,i+2,pointsum);
                pointsum--;
                s=s.Substring(0,i+1)+s.Substring(i+2);
            }else
            {
                break;
            }
        }
    }
    public bool Isvalid(string s,int start,int end)
    {
        if(start>end)
        {
            return false;
        }
        if(s[start]=='0'&&start!=end)
        {
            return false;
        }
        int num=0;
        for(int i=start;i<=end;i++)
        {
            if(s[i]>'9'||s[i]<'0')
            {
                return false;
            }
            num=num*10+(s[i]-'0');
            if(num>255)
            {
                return false;
            }
        }
        return true;
    }
}

本题的结束条件就是Ip地址的分割点为3个就收集Path,但是除了这个还要判断是否地址合理在0-255的范围内,如果合法就打上分隔符,然后递归,然后回溯,最终返回所收集到的结果。

78.子集

public class Solution {
    List<int> path=new List<int>();
    List<IList<int>> result=new List<IList<int>>();
    public IList<IList<int>> Subsets(int[] nums) {
        backtracking(nums,0);
        return result;
    }
    public void backtracking(int[] nums,int startIndex)
    {

        result.Add(new List<int>(path));
        for(int i=startIndex;i<nums.Length;i++)
        {
            path.Add(nums[i]);
            backtracking(nums,i+1);
            path.RemoveAt(path.Count-1);
        }
    }
}

自己收进Path的条件是直接收集就行,但要注意Startindex的取值是I+1,因为不能有重复的。

90.子集II

public class Solution {
    List<int> path=new List<int>();
    List<IList<int>> result=new List<IList<int>>();
    bool[] used;
    public IList<IList<int>> SubsetsWithDup(int[] nums) {
        used=new bool[nums.Length];
        for(int i=0;i<used.Length;i++)  
        {  
            used[i]=false; 
        }
        Array.Sort(nums);
        backtracking(nums,0,used);
        return result;
    }
    public void backtracking(int[] nums,int startIndex,bool[] used)
    {

        result.Add(new List<int>(path));
        for(int i=startIndex;i<nums.Length;i++)
        {
            if (i>0&&nums[i]==nums[i-1]&&used[i-1]==false)
            {
                continue;
            }
            path.Add(nums[i]);
            used[i]=true;
            backtracking(nums,i+1,used);
            used[i]=false;
            path.RemoveAt(path.Count-1);
        }
    }
}

在上一题的基础上加入了一个Used的Bool类型数组,因为我们需要在树层上剪枝,树枝上保留,所以如果当树层向下遇到了两个相邻的相同元素,就去看前一个的Used数组是否为False,如果是就跳过,否则就加入Path,最终返回即可。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值