8.4 Write a method to compute all permutations of a string


#include <string>
#include <map>
#include <deque>
#include <iostream>

using namespace std;

void helper(map<char, int>& charMap, string str, int size)
{
    if (size == 0)
    {
        cout << str << endl;
        return;
    }
    else
    {
        for (map<char, int>::iterator it = charMap.begin(); it != charMap.end(); ++it)
        {
            if (charMap[it->first] != 0)
            {
                -- charMap[it->first];
                str.push_back(it->first);
                --size;
                helper(charMap, str, size);
                ++size;
                str.erase(str.end() - 1);
                ++ charMap[it->first];
            }
        }
    }
}

void printAllPerms(string str)
{
   map<char, int> charMap;
   for (string::iterator it = str.begin(); it != str.end(); ++it)
   {
       charMap[*it] ++;
   }
   helper(charMap, "", str.size());
}

void printAllPerms_iterative(string str)
{
    map<char, int> charMap;
    for (string::iterator it = str.begin(); it != str.end(); ++it)
    {
        charMap[*it] ++;
    }
    
    
    map<char, int> top;
    int size;
    string perm;
    
    deque<map<char, int> > stack;
    deque<char> stack_char;
    deque<int> stack_size;
    
    stack.push_back(charMap);
    stack_char.push_back('^');
    stack_size.push_back(str.size());
    
    while (! stack.empty())
    {
        top = stack.back();
        stack.pop_back();
        
        size = stack_size.back();
        stack_size.pop_back();
        
        perm.push_back(stack_char.back());
        stack_char.pop_back();
        
        if (size > 0)
        {
            for (map<char, int>::iterator it = top.begin(); it != top.end(); ++it)
            {
                if (top[it->first] > 0)
                {
                    -- top[it->first];
                    -- size;
                    stack.push_back(top);
                    stack_char.push_back(it->first);
                    stack_size.push_back(size);
                    ++ size;
                    ++ top[it->first];
                }
            }
        }
        else
        {
            cout << perm << endl;
            int i = 0;
            while ((! stack_size.empty()) && i <= stack_size.back())
            {
                perm.erase(perm.end() - 1);
                i ++;
            }
        }
    }
}

int main()
{
    string str("12242");
    printAllPerms(str);
    printAllPerms_iterative(str);
    return 0;
}

Leave a comment