zoukankan      html  css  js  c++  java
  • 算法-哈希表

    1.给定一个包含大写字母和小写字母的字符串,找到通过这些字母构造成的最长的回文串。

    在构造过程中,请注意区分大小写。比如 "Aa" 不能当做一个回文字符串。

    注意:
    假设字符串的长度不会超过 1010。

    示例 1:

    输入:
    "abccccdd"

    输出:
    7

    解释:
    我们可以构造的最长的回文串是"dccaccd", 它的长度是 7。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/longest-palindrome
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    class Solution {
    public:
        int longestPalindrome(string s) {
            map<char,int> nums;
            for(int i=0;i<s.size();++i){
                nums[s[i]]++;
            }
            int count=0;
            bool hasSingleChar=false;
            for(auto c:nums){
                if(c.second % 2 ==0) count+=c.second;
                else{ 
                    hasSingleChar=true;
                    count+=c.second-1;;
                }
            }
            count+=hasSingleChar;
            return count;
        }
    };
    class Solution {
    public:
        int longestPalindrome(string s) 
        {
            int n=s.length();
            unordered_map<char,int> tmp;
            for(int i=0;i<n;i++)
            {
                tmp[s[i]]++;
            }
            unordered_map<char,int>::iterator it;
            for(it=tmp.begin();it!=tmp.end();it++)
            {
                if(it->second%2==1)
                {
                    n--;
                }
            }
            if(n==s.length())
            {
                return n;
            }
            else
            {
                return n+1;
            }
        }
    };

    2.给定一种规律 pattern 和一个字符串 str ,判断 str 是否遵循相同的规律。

    这里的 遵循 指完全匹配,例如, pattern 里的每个字母和字符串 str 中的每个非空单词之间存在着双向连接的对应规律。

    示例1:

    输入: pattern = "abba", str = "dog cat cat dog"
    输出: true

    示例 2:

    输入:pattern = "abba", str = "dog cat cat fish"
    输出: false

    示例 3:

    输入: pattern = "aaaa", str = "dog cat cat dog"
    输出: false

    示例 4:

    输入: pattern = "abba", str = "dog dog dog dog"
    输出: false

    说明:
    你可以假设 pattern 只包含小写字母, str 包含了由单个空格分隔的小写字母。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/word-pattern
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    vector<string> split(string str){
        str.push_back(' ');//加个空格,避免处理边界条件!!!
        vector<string> strs;
        string s="";
        for(int i=0;i<str.size();++i){
             if(str[i]!=' ') s+=str[i];
             else {
                 strs.push_back(s);
                 s="";
             }
         }
        return strs;
     }
    class Solution {
    public:
        bool wordPattern(string pattern, string str) {
            vector<string> strs=split(str);
            if(strs.size()!=pattern.size()) return false;
            unordered_map<string,char> str_to_char_map;//两个哈希表,形成映射
            unordered_map<char,string> char_to_str_map;
            for(int i=0;i<strs.size();++i){
                if(str_to_char_map.find(strs[i])!=str_to_char_map.end()){
                    if(str_to_char_map[strs[i]]==pattern[i])
                        continue;
                    else return false;
                }else{                
                    if(char_to_str_map.find(pattern[i])==char_to_str_map.end()){
                        str_to_char_map[strs[i]]=pattern[i];
                        char_to_str_map[pattern[i]]=strs[i];
                    }else{
                        if(char_to_str_map[pattern[i]]!=strs[i]) return false;
                    }
                }
            }
            return true;
        }
    };
    vector<string> split(string str){
        str.push_back(' ');//加个空格,避免处理边界条件!!!
        vector<string> strs;
        string s="";
        for(int i=0;i<str.size();++i){
             if(str[i]!=' ') s+=str[i];
             else {
                 strs.push_back(s);
                 s="";
             }
         }
        return strs;
     }
    class Solution {
    public:
        bool wordPattern(string pattern, string str) {
            vector<string> strs=split(str);
            if(strs.size()!=pattern.size()) return false;
            unordered_map<string,char> str_to_char_map;//两个哈希表,形成映射
            char used[128]={0};//检测字母是否已经映射过
            for(int i=0;i<strs.size();++i){
                if(str_to_char_map.find(strs[i])!=str_to_char_map.end()){
                    if(str_to_char_map[strs[i]]==pattern[i])
                        continue;
                    else return false;
                }else{                
                    if(used[pattern[i]]) return false;
                    else {
                        str_to_char_map[strs[i]]=pattern[i];
                        used[pattern[i]]=1;
                    }
                }
            }
            return true;
        }
    };

    3.给定一个字符串数组,将字母异位词组合在一起。字母异位词指字母相同,但排列不同的字符串。

    示例:

    输入: ["eat", "tea", "tan", "ate", "nat", "bat"],
    输出:
    [
      ["ate","eat","tea"],
      ["nat","tan"],
      ["bat"]
    ]

    说明:

        所有输入均为小写字母。
        不考虑答案输出的顺序。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/group-anagrams
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    /*排序字符串相同的映射到一个key下,key为已排序的字符串*/
    class Solution {
    public:
        vector<vector<string>> groupAnagrams(vector<string>& strs) {
            
            int len=strs.size();
            vector<vector<string>> res;
            unordered_map<string,vector<string>> map;
            string temp;
            for(int i=0;i<len;++i){
                temp=strs[i];
                sort(temp.begin(),temp.end());//字符串排序得到key值
                if(map.find(temp)==map.end()){
                    vector<string> item;/*如果表中没有,则创建vector,加到表中*/
                    map[temp]=item;
                }
                map[temp].push_back(strs[i]); /*加到key下的vector*/     
            }
            unordered_map<string,vector<string>>::iterator it;
            for(it=map.begin();it!=map.end();it++){
                res.push_back((*it).second);
            }
            return res;
        }
    };
    vector<int> numsOfEveryChar(string str){
        vector<int> nums;
        for(int i=0;i<26;++i){
            nums.push_back(0);
        }
        for(int i=0;i<str.length();++i){
            nums[str[i]-'a']++;
        }
        return nums;
    }
    class Solution {
    public:
        vector<vector<string>> groupAnagrams(vector<string>& strs) {
            
            int len=strs.size();
            vector<vector<string>> res;
            map<vector<int>,vector<string>> m;
            vector<int> num;
            for(int i=0;i<len;++i){
                num=numsOfEveryChar(strs[i]);
                if(m.find(num)==m.end()){
                    vector<string> list;                
                    m[num]=list;
                }
                m[num].push_back(strs[i]);
            }
            map<vector<int>,vector<string>>::iterator it;
            for(it=m.begin();it!=m.end();it++){
                res.push_back((*it).second);
            }
            return res;
        }
    };

    4.给定一个字符串,请你找出其中不含有重复字符的 最长子串 的长度。

    示例 1:

    输入: "abcabcbb"
    输出: 3
    解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。

    示例 2:

    输入: "bbbbb"
    输出: 1
    解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。

    示例 3:

    输入: "pwwkew"
    输出: 3
    解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。
         请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/longest-substring-without-repeating-characters
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    class Solution {
    public:
        int lengthOfLongestSubstring(string s) {
            int n=s.size(),res=0;
            int index[128]={0};
            for(int j=0,i=0;j<n;j++){
                i=max(index[  s[j]  ],i);//刷新开始点,为当前遇到字符的前面所存储的索引后一个索引
                res=max(res,j-i+1);//更新结果
                index[   s[j]   ]=j+1;//index指向该字符索引的后面一个索引
            }
            return res;  
        }
    };

    5.所有 DNA 由一系列缩写为 A,C,G 和 T 的核苷酸组成,例如:“ACGAATTCCG”。在研究 DNA 时,识别 DNA 中的重复序列有时会对研究非常有帮助。

    编写一个函数来查找 DNA 分子中所有出现超多一次的10个字母长的序列(子串)。

    示例:

    输入: s = "AAAAACCCCCAAAAACCCCCCAAAAAGGGTTT"

    输出: ["AAAAACCCCC", "CCCCCAAAAA"]

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/repeated-dna-sequences
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    class Solution {
    public:
        vector<string> findRepeatedDnaSequences(string s) {
            unordered_map<string,int> m;
            vector<string> res;
            string temp;
            for(int i=0;i<s.size();++i){
                temp=s.substr(i,10);
                if(m.find(temp)==m.end()){
                    m[temp]=1;
                }else{
                    m[temp]++; 
                }
                           
            }
            unordered_map<string,int>::iterator it;
            for(it=m.begin();it!=m.end();++it){
                if(it->second>1) res.push_back(it->first);  
            }
            return res;
        }
    };

    6.给你一个字符串 S、一个字符串 T,请在字符串 S 里面找出:包含 T 所有字母的最小子串。

    示例:

    输入: S = "ADOBECODEBANC", T = "ABC"
    输出: "BANC"

    说明:

        如果 S 中不存这样的子串,则返回空字符串 ""。
        如果 S 中存在这样的子串,我们保证它是唯一的答案。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/minimum-window-substring
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    unordered_map<char,int> charnums(string t){
        unordered_map<char,int> nums;
        for(int c=0;c<128;c++){
            nums[c]=0;
        }
        for(int i=0;i<t.size();++i){
            nums[t[i]]++;
        }
        return nums;
    }
    class Solution {
    public:
        string minWindow(string s, string t) {
            int n=s.size(),left=0,right=0,res=s.size(),count=0,resleft=0;
            unordered_map<char,int> charCountOfT=charnums(t);
            unordered_map<char,int> charCountOfS;
            for(int i=0;i<n;++i){
                if(t.find(s[i])!=-1){
                    if(charCountOfS.find(s[i])==charCountOfS.end()){
                        charCountOfS[s[i]]=1;
                        count++;                   
                    }else{
                        charCountOfS[s[i]]++;
                        if(charCountOfS[s[i]]<=charCountOfT[s[i]]){
                            count++;
                        }
                    }
                     
                    //达到包含所有字符后缩减窗口大小
                    if(count==t.size()){
                        right=i;
                        while(left<=right){
                            if(t.find(s[left])==-1){
                                left++;                            
                            }else{
                                if(charCountOfS[s[left]]>charCountOfT[s[left]]){ 
                                    charCountOfS[s[left]]--;
                                    left++;
                                }else{
                                    if(right-left<res) {
                                        res=right-left;
                                        resleft=left;
                                    }                                    
                                    break;
                                }
                            }
                        }
                    }      
                }  
            }
            if(count<t.size()) return "";
            return s.substr(resleft,res+1);
        }
    };
  • 相关阅读:
    挖地雷——线性dp
    hdu6376 度度熊剪纸条-----01背包
    Problem
    UVa 10635
    Vjudge_题目分享_A -> 线性Dp排列木棍 ( Dilworth定理应用
    洛谷日报 & 原来博客(转载)
    使用.net6 WebApplication打造最小API
    k8s笔记——NodePort暴露nginx-controller实现https自动跳转自定义nodePort端口
    通过Dapr实现一个简单的基于.net的微服务电商系统(十七)——服务保护之动态配置与热重载
    通过Dapr实现一个简单的基于.net的微服务电商系统(十六)——dapr+sentinel中间件实现服务保护
  • 原文地址:https://www.cnblogs.com/chendaniu/p/10199500.html
Copyright © 2011-2022 走看看