• 【LeetCode】49. Anagrams (2 solutions)


    Anagrams

    Given an array of strings, return all groups of strings that are anagrams.

    Note: All inputs will be in lower-case.

    首先解释一下什么是anagrams:在不考虑顺序的情况下,包含相同字母的字符串组成anagrams

    例如:

    1、{"eat","ate","tea","coffee"}的anagrams是{"eat","ate","tea"}

    2、{"tea","and","ate","eat","dan"}的anagrams是{"tea","ate","eat","and","dan"}

    解法一:排序之后的string作为key

    在具体实现过程中,构造了两张映射表dict和exist

    dict用来对排序过的单词进行快速查找,值(value)为第一个该编码的单词下标。

    exist用来记录该排序过的单词是否已存在anagrams中,

    如果是,只需要将当前单词装入anagrams;

    如果不是,首先要将存放在m中的代表该排序过的单词的第一个单词装入anagrams,再装入当前单词。

    class Solution {
    public:
        vector<string> anagrams(vector<string> &strs) {
            vector<string> ret;
            unordered_map<string, int> dict;
            unordered_map<string, bool> exist;
            
            for(int i = 0; i < strs.size(); i ++)
            {
                string temp = strs[i];
                sort(temp.begin(), temp.end());
                if(dict.find(temp) == dict.end())
                    dict[temp] = i;
                else
                {//find anagrams
                    if(exist[strs[dict[temp]]] == false)
                    {
                        ret.push_back(strs[dict[temp]]);
                        exist[strs[dict[temp]]] = true;
                    }
                    ret.push_back(strs[i]);
                    exist[strs[i]] = true;
                }
            }
            
            return ret;
        }
    };

    解法二:利用质因数分解

    背景:任何一个正整数都可以分解为唯一的质因数乘积:n=2a3b5c7d

    因此n可以用{a,b,c,d}来唯一表示。

    对于这个题,我们对a~z每个单词的出现次数作为每个质因数的次幂,

    将乘积进行唯一编码,就可以忽略字母顺序了。相同编码的单词组成anagrams。

    因为共有小写字母26个,因此我们需要前26个质因数。

    在具体实现过程中,我还构造了两张映射表m和exist

    dict用来对编码进行快速查找,值(value)为第一个该编码的单词下标。

    exist用来记录该编码是否已存在anagrams中,

    如果是,只需要将当前单词装入anagrams;

    如果不是,首先要将存放在dict中的代表该编码的第一个单词装入anagrams,再装入当前单词。

    class Solution {
    public:
        vector<string> anagrams(vector<string> &strs) {
            vector<string> ret;
            vector<long long int> code(strs.size(), 0);
            CalCode(strs, code);
            map<long long int, int> dict;
            map<string, bool> exist;
            
            for(int i = 0; i < strs.size(); i ++)
            {
                if(dict.find(code[i]) == dict.end())
                    dict[code[i]] = i;
                else
                {
                    if(exist[strs[dict[code[i]]]] == false)
                    {
                        exist[strs[dict[code[i]]]] = true;
                        ret.push_back(strs[dict[code[i]]]);
                    }
                    exist[strs[i]] = true;
                    ret.push_back(strs[i]);
                }
            }
            return ret;
        }
        void CalCode(vector<string> &strs, vector<long long int> &code)
        {
            for(int i = 0; i < strs.size(); i ++)
            {
                string cur = strs[i];
                vector<int> count(26, 0); //a~z count
                for(int j = 0; j < cur.size(); j ++)
                {
                    count[cur[j]-'a'] ++;
                }
                double prime[26] = {2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101};
                long long result = 1;
                for(int j = 0; j < 26; j ++)
                {
                   result *= (long long int)pow(prime[j], count[j]);
                }
                code[i] = result;
            }
        }
    };

  • 相关阅读:
    将Excel嵌入你的.Net程序
    调用资源文件
    Socket Error# Description
    LPCTSTR 和其它
    linux send and recv详解
    stdafx.h的作用
    setsocketopt() usage
    openfire源码入门级分析
    openfire分析
    关于xmpp
  • 原文地址:https://www.cnblogs.com/ganganloveu/p/4161264.html
Copyright © 2020-2023  润新知