【数据结构C++】字符串(四)

4. 字符串

  • 旋转字符串: https://leetcode-cn.com/problems/rotate-string/
    【数据结构C++】字符串(四)_第1张图片

    class Solution {
    public:
        bool rotateString(string s, string goal) {
            // s+s=abcdeabcde  在重复的字符串中寻找目标
            // find函数在找不到指定值得情况下会返回string::npos
            return s.size() == goal.size() && (s + s).find(goal) != string::npos;
        }
    };
    
  • 翻转字符串里的单词: https://leetcode-cn.com/problems/reverse-words-in-a-string/
    【数据结构C++】字符串(四)_第2张图片
    【数据结构C++】字符串(四)_第3张图片
    【数据结构C++】字符串(四)_第4张图片
    【数据结构C++】字符串(四)_第5张图片

    class Solution {
    public:
        string reverseWords(string s) {
            // 反转整个字符串
            reverse(s.begin(), s.end());
    
            int n = s.size();
            int idx = 0;
            for (int start = 0; start < n; start++) {
                if (s[start] != ' ') {
                    // 填一个空白字符然后将idx移动到下一个单词的开头位置
                    if (idx != 0) s[idx++] = ' ';
    
                    // 循环遍历至单词的末尾
                    int end = start;
                    while (end < n && s[end] != ' ') s[idx++] = s[end++];
    
                    // 反转整个单词
                    reverse(s.begin() + idx - (end - start), s.begin() + idx);
    
                    // 更新start,去找下一个单词
                    start = end;
                }
            }
            s.erase(s.begin() + idx, s.end());
            return s;
        }
    };
    
    复杂度分析
    时间复杂度:O(n),其中 n 为输入字符串的长度。
    空间复杂度: O(1) 的额外空间来存放若干变量。
    
  • 有效的字母异位词: https://leetcode-cn.com/problems/valid-anagram/
    【数据结构C++】字符串(四)_第6张图片
    在这里插入图片描述

    class Solution {
    public:
        bool isAnagram(string s, string t) {
            if (s.length() != t.length()) {
                return false;
            }
            sort(s.begin(), s.end());
            sort(t.begin(), t.end());
            return s == t;
        }
    };
    
    复杂度分析
    时间复杂度:O(nlogn),其中 n 为 s 的长度。排序的时间复杂度为 O(nlogn),比较两个字符串是否相等时间复杂度为 O(n),因此总体时间复杂度为O(nlogn+n)=O(nlogn)。
    空间复杂度:O(logn)。排序需要O(logn) 的空间复杂度。注意,在某些语言(比如 Java & JavaScript)中字符串是不可变的,因此我们需要额外的O(n) 的空间来拷贝字符串。但是我们忽略这一复杂度分析,因为:
    这依赖于语言的细节;
    这取决于函数的设计方式,例如,可以将函数参数类型更改为 char[]
  • 最长回文串: https://leetcode-cn.com/problems/longest-palindrome/
    【数据结构C++】字符串(四)_第7张图片
    【数据结构C++】字符串(四)_第8张图片

    class Solution {
    public:
        int longestPalindrome(string s) {
            unordered_map<char, int> count;  //创建哈希表
            int ans = 0;
            for (char c : s)
                ++count[c];
            for (auto p : count) {
                int v = p.second;   //second指向值
                ans += v / 2 * 2;
                if (v % 2 == 1 and ans % 2 == 0)
                    ++ans;
            }
            return ans;
        }
    };
    
    复杂度分析
    时间复杂度:O(N),其中 N 为字符串 s 的长度。我们需要遍历每个字符一次。
    空间复杂度:O(S),其中 S 为字符集大小。 
    
  • 同构字符串: https://leetcode-cn.com/problems/isomorphic-strings/
    【数据结构C++】字符串(四)_第9张图片
    【数据结构C++】字符串(四)_第10张图片

    class Solution {
    public:
        bool isIsomorphic(string s, string t) {
            unordered_map<char, char> s2t;  //s中的值(x = s[i])为键,y = t[i]为值
            unordered_map<char, char> t2s;  //t中的值 (y = t[i])为键,x = s[i]为值
            int len = s.length();
            for (int i = 0; i < len; i++) {
                char x = s[i], y = t[i];
                if ((s2t.count(x) && s2t[x] != y) || (t2s.count(y) && t2s[y] != x)) {
                    return false;
                }
                s2t[x] = y;
                t2s[y] = x;
            }
            return true;
        }
    };
    
    复杂度分析
    时间复杂度:O(n),其中 n 为字符串的长度。我们只需同时遍历一遍字符串 s 和 t 即可。
    空间复杂度:O(∣Σ∣),其中Σ 是字符串的字符集。哈希表存储字符的空间取决于字符串的字符集大小,最坏情况下每个字符均不相同,需 		
    要 O(∣Σ∣) 的空间。
    
  • 回文子串: https://leetcode-cn.com/problems/palindromic-substrings/
    【数据结构C++】字符串(四)_第11张图片
    【数据结构C++】字符串(四)_第12张图片在这里插入图片描述

    class Solution {
    public:
        int countSubstrings(string s) {
            int n = s.size(), ans = 0;
            for (int i = 0; i < 2 * n - 1; ++i) {
                int l = i / 2, r = i / 2 + i % 2;
                while (l >= 0 && r < n && s[l] == s[r]) {
                    --l;
                    ++r;
                    ++ans;
                }
            }
            return ans;
        }
    };
    
    复杂度分析
    时间复杂度:O(n^2)。
    空间复杂度:O(1)
  • 回文数: https://leetcode-cn.com/problems/palindrome-number/
    【数据结构C++】字符串(四)_第13张图片
    【数据结构C++】字符串(四)_第14张图片
    【数据结构C++】字符串(四)_第15张图片

    class Solution {
    public:
        bool isPalindrome(int x) {
            // 特殊情况:
            // 如上所述,当 x < 0 时,x 不是回文数。
            // 同样地,如果数字的最后一位是 0,为了使该数字为回文,
            // 则其第一位数字也应该是 0
            // 只有 0 满足这一属性
            if (x < 0 || (x % 10 == 0 && x != 0)) {
                return false;
            }
    
            int revertedNumber = 0;
            while (x > revertedNumber) {
                revertedNumber = revertedNumber * 10 + x % 10;
                x /= 10;
            }
    
            // 当数字长度为奇数时,我们可以通过 revertedNumber/10 去除处于中位的数字。
            // 例如,当输入为 12321 时,在 while 循环的末尾我们可以得到 x = 12,revertedNumber = 123,
            // 由于处于中位的数字不影响回文(它总是与自己相等),所以我们可以简单地将其去除。
            return x == revertedNumber || x == revertedNumber / 10;
        }
    };
    
    复杂度分析
    时间复杂度:O(logn),对于每次迭代,我们会将输入除以 10,因此时间复杂度为 O(logn)。
    空间复杂度:O(1)。我们只需要常数空间存放若干变量。
    
  • 计数二进制子串: https://leetcode-cn.com/problems/count-binary-substrings/
    【数据结构C++】字符串(四)_第16张图片
    【数据结构C++】字符串(四)_第17张图片

    class Solution {
    public:
        int countBinarySubstrings(string s) {
            int ptr = 0, n = s.size(), last = 0, ans = 0;
            while (ptr < n) {
                char c = s[ptr];
                int count = 0;
                while (ptr < n && s[ptr] == c) {
                    ++ptr;
                    ++count;
                }
                ans += min(count, last);
                last = count;
            }
            return ans;
        }
    };
    
    复杂度分析
    时间复杂度:O(n)。
    空间复杂度:O(1)

你可能感兴趣的:(数据结构,c++,字符串)