leetcode 7月26日 非作弊刷题

3. Longest Substring Without Repeating Characters

Given a string, find the length of the longest substring without repeating characters.

Examples:

Given "abcabcbb", the answer is "abc", which the length is 3.

Given "bbbbb", the answer is "b", with the length of 1.

Given "pwwkew", the answer is "wke", with the length of 3. Note that the answer must be a substring"pwke" is a subsequence and not a substring.

思路:用哈希表存储已经检查过的子母。用一个变量存储当前的最大长度。从第一个字符开始,每更换首字母,哈希表都要清空,时间复杂度和空间复杂度都是O(n2)

class Solution {
public:
    int lengthOfLongestSubstring(string s) {
        unordered_set<char> storedChar;
        int n=s.size();
        if(n<=1) return n;
        int sum=1;
        for(int i=0;i<n;i++)
        {
            int j=0;
            int tempsum=1;
            storedChar.insert(s[i]);
            for(int j=i+1;j<n;j++)
            {
                if(storedChar.find(s[j])!=storedChar.end()) 
                {
                    storedChar.clear();
                    break;
                }
                else 
                {
                    tempsum++; 
                    storedChar.insert(s[j]);
                }
                
            }
            if(sum<tempsum) sum=tempsum;//这个要放在判断语句的外边,才能保证都执行到
            if(j==n) break;//如果已经有一个遍历到最后,那后面没有再遍历的必要了
        }
        return sum;
    }
};

双指针+哈希表(固定数组)

大神解法1:时间复杂度是n,空间复杂度是常数。这种方法实际上是双指针的方法。

因为只有256个字符,定义一个256长度的矩阵,矩阵中存储每个字符最后出现的位置。

定义一个变量start,这个变量的初始值是-1,它保存的是当前字符之前最后一个重复字符的第一个字符的位置。如aabbc,如果当前遍历到c,那么start保存的是第一个b的位置。

class Solution {
public:
    int lengthOfLongestSubstring(string s) {
        vector<int> de(256,-1);
        int result=0;
        int j=-1;
        for(int i=0;i<s.size();i++)
        {
            if(de[s[i]]>j)//如果之前有重复的字符,这里使用大于号,为了移动j指针到最新的重复值上去。
                j=de[s[i]];
            de[s[i]]=i;
            result =max(result,i-j);
        }
        return result;
    }
};

最多推荐解法:

与上面的方法基本上一样,只不过使用的是哈希表,变量的初始值也不是0,将第二个指针移动到最近的重复字符,最左边的右边一个位置。这种方法更容易理解题目使用双指针和哈希表的原理。

这里编程需要注意的是,由于map的特点,还没有存储的字符默认的键值是0,所以为了与初始零位区别,存储的键值从1开始算。

另外一个需要注意的是:判断移动j指针的条件需要仔细考虑。

class Solution {
public:
    int lengthOfLongestSubstring(string s) {
        unordered_map<char,int> decide;//键是字符,值是标号的位置
        int n=s.size();
        int result=0;
        int j=0;
        for(int i=0;i<n;i++)
        {
            if(decide[s[i]]>j)//注意这里的判断条件
                j=decide[s[i]];
                decide[s[i]]=i+1;
            result=max(result,i-j+1);     
        }
        return result;
    }
};

7. Reverse Integer

Reverse digits of an integer.

Example1: x = 123, return 321
Example2: x = -123, return -321

14.Longest Common Prefix 舍弃

求一组string的最长公共前缀
class Solution {
public:
    string longestCommonPrefix(vector<string>& strs) {
        int n=strs.size();
        string result;
        if(n==0) return result;
        string flag=strs[0];
        int m=flag.size();
        for(int i=0;i<m;i++)
        {
            for(int j=1;j<n;j++)
        {
            if(flag[i]!=strs[j][i]) 
            return result;
        }
            result.push_back(flag[i]);
        }
        return result;

    }
};

20. Valid Parentheses 有效括号

Given a string containing just the characters '('')''{''}''[' and ']', determine if the input string is valid.

The brackets must close in the correct order, "()" and "()[]{}" are all valid but "(]" and "([)]" are not.

判断一个字符串是否是有效的括号组合

思路,依次将这些字符入栈,判断栈顶元素与当前元素是否是对应上的,是则pop,不是则入栈,到最后判断栈是否为空。

class Solution {
public:
    bool isValid(string s) {
        stack<char> result;
        int n=s.size();
        if(n==0) return true;
     for(int i=0;i<n;i++)
            {
                if(result.empty())
                    result.push(s[i]);
                else if(result.top()=='('&&s[i]==')'||
                      result.top()=='['&&s[i]==']'||
                      result.top()=='{'&&s[i]=='}') 
                        result.pop();
                else
                    result.push(s[i]);
                
            }
            return result.empty();
    }
};

别人的思路:

这种方法能够更快的判断不符合条件的字符串,不需要将字符串遍历完成。

class Solution {
public:
    bool isValid(string s) {
        stack<char> paren;
        for (char& c : s) {
            switch (c) {
                case '(': 
                case '{': 
                case '[': paren.push(c); break;
                case ')': if (paren.empty() || paren.top()!='(') return false; else paren.pop(); break;
                case '}': if (paren.empty() || paren.top()!='{') return false; else paren.pop(); break;
                case ']': if (paren.empty() || paren.top()!='[') return false; else paren.pop(); break;
                default: ; // pass
            }
        }
        return paren.empty() ;
    }
};

注意:只要当前的字符是)}]三个的一个,如果不能与栈顶结合,那就说明这个字符串是错误的。比如下面的代码。

class Solution {
public:
    bool isValid(string s) {
        stack<char> result;
        for(auto & a:s){
            if(a=='(') result.push(')');
            else if(a=='{') result.push('}');
            else if(a=='[')  result.push(']');
            else if(result.empty()||result.top()!=a)//这里直接出栈判断
                return false;
            else result.pop();
        }
        return result.empty();
    }
};

38. Count and Say

The count-and-say sequence is the sequence of integers with the first five terms as following:

1.     1
2.     11
3.     21
4.     1211
5.     111221

1 is read off as "one 1" or 11.
11 is read off as "two 1s" or 21.
21 is read off as "one 2, then one 1" or 1211.

Given an integer n, generate the nth term of the count-and-say sequence.

Note: Each term of the sequence of integers will be represented as a string.

Example 1:

Input: 1
Output: "1"

Example 2:

Input: 4
Output: "1211"
根据题意写的代码
class Solution {
public:
    string countAndSay(int n) {
        string res;
        res+=to_string(1);
        if(n==1) return res;
        for(int i=2;i<=n;i++)
        {
            string temp;
            int num=1;
            for(int j=0;j<res.size();j++)
            {
                while(j+1!=res.size())
                {
                    if(res[j]==res[j+1]) 
                    {
                        j++;
                        num++;
                    }
                    else break;
                }
            temp+=to_string(num);
                temp+=to_string(res[j]);//错误处在这
//改:temp+=res[j];
                num=1;
            }
            res=temp;
        }
        return res;
    }
};
69. Sqrt(x)

Implement int sqrt(int x).

Compute and return the square root of x.

这个题目的意思是找到一个整数的整数平方根。
思路:
先除以2,直到在范围之内。保存最后两个值。
以后做二分查找。

412. Fizz Buzz

Write a program that outputs the string representation of numbers from 1 to n.

But for multiples of three it should output “Fizz” instead of the number and for the multiples of five output “Buzz”. For numbers which are multiples of both three and five output “FizzBuzz”.

Example:

n = 15,

Return:
[
    "1",
    "2",
    "Fizz",
    "4",
    "Buzz",
    "Fizz",
    "7",
    "8",
    "Fizz",
    "Buzz",
    "11",
    "Fizz",
    "13",
    "14",
    "FizzBuzz"
]
class Solution {
public:
    vector<string> fizzBuzz(int n) {
        vector<string> result;
        string five="Buzz";
        string three="Fizz";
        string fth="FizzBuzz";
        for(int i=1;i<=n;i++)
        {
            if(i%3==0&&i%5==0) result.push_back(fth);
            else if(i%3==0) result.push_back(three);
            else if(i%5==0) result.push_back(five);
            else 
            {
                string temp;
               temp+=to_string(i);//记住这个用法
                result.push_back(temp);
            }
        }
        return result;
    }
};

简单的代码,下面的代码使用string的+特性,少一个判断。初始化时,string是空的。

class Solution {
public:
    vector<string> fizzBuzz(int n) {
        vector<string> result(n);
        for(int i=1;i<=n;i++)
        {
            if(i%3==0) result[i-1]+="Fizz";
            if(i%5==0) result[i-1]+="Buzz";
            if(result[i-1].empty())
                result[i-1]+=to_string(i);
        }
        return result;
    }
};







  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值