欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

重复的DNA序列

程序员文章站 2022-06-08 12:24:02
...

重复的DNA序列

方法一:

枚举所有长度为10的子串,插入到哈希表中,记录数量。遍历哈希表,存储出现次数超过1次的子串。复杂度O(N)

class Solution {
public:
    vector<string> findRepeatedDnaSequences(string s) {
        map<string,int> word_map;//<子串,子串数量>
        for(int i =0;i<s.size() ;++i)
        {
            string str = s.substr(i,10);
            if(word_map.find(str) != word_map.end())
            {
                word_map[str]++;
            }else{
                word_map[str] = 1;
            }
        }
        
        vector<string> res;
        for(auto p = word_map.begin();p!=word_map.end();++p)
        {
            if(p->second > 1)
                res.push_back(p->first);
        }
        
        return res;
    }
};


方法2:

将长度为10的DNA序列编码:A,C,G,T四个字符分别用0,1,2,3(00,01,10,11)表示,所以

AAAAACCCCT->最低位00 00 00 00 00 01 01 01 01 11最高位,表示成 11 01 01 01 01 00 00 00 00 00 = 873472

1.设置全局整数hash, int hash_map[1048576],1048576 = 2^20,表示所有长度为10的DNA序列

2.将DNA字符串的前10个字符使用左移位运算转换为整数key,hash_map[key]++

3.从第11个字符开始,按顺序遍历各个字符,遇到1个字符,就将key右移2位(就是去掉最低位的意思),然后将新的字符转为整数后,或运算 到最高位(19,20这两位),hash_map[key]++

key= key >> 2;

key = key |(A(00) << 18);

4.遍历哈希表,若hash_map[i]>1,将i从低位到高位转换为10个字符的DNA序列,push到结果。

int hash_map[1048576] = {0};//哈希太大,需要全局数组

class Solution {
public:
    vector<string> findRepeatedDnaSequences(string s) {
        vector<string> res;
        if(s.size() < 10)
            return res;
        
        for(long i = 0;i<1048576;++i)////每次调用需要更新全局数组
            hash_map[i] = 0;
        
        long char_map[128] ={0};
        char_map['A'] = 0;
        char_map['C'] = 1;
        char_map['G'] = 2;
        char_map['T'] = 3;
        
        long key = 0;
        for(int i =9;i>=0;--i)//将前10个字符先转为key
            key = (key <<2) + char_map[s[i]];
        
        hash_map[key] = 1;
        
        for(int i =10;i<s.length();++i)//从第10个字符开始,先去掉最低位的字符,再把新的最高位的添加上去
        {
            key = key >> 2;
            key = key | (char_map[s[i]] << 18);
            hash_map[key]++;
        }
        
        for(long i =0;i<1048576;i++)
        {
            if(hash_map[i] > 1)
                res.push_back(change_int_to_DNA(i));
        }
        
        return res;
    }
    
    string change_int_to_DNA(long DNA)
    {
        const char DNA_CHAR[] = {'A','C','G','T'};
        string str;
        for(int i = 0;i<10;++i)//将编码还原成DNA序列
        {
            str += DNA_CHAR[DNA & 3];
            DNA = DNA >> 2;
        }
        return str;
    }
    
};

相关标签: LeetCode