C++에서 목록 항목 집합 (지도 형식으로 입력)의 가능한 모든 조합을 제공하는 알고리즘을 만들려고합니다. 나는 중복을 피하고 모든 가능한 조합을 포함하고 싶다. 내가 알고리즘에이지도를 공급 것형식 알고리즘에 의한 목록 조합
map<string, vector<string> > sandwichMap;
sandwichMap["bread"].push_back("wheat");
sandwichMap["bread"].push_back("white");
sandwichMap["meat"].push_back("ham");
sandwichMap["meat"].push_back("turkey");
sandwichMap["meat"].push_back("roastbeef");
sandwichMap["veggie"].push_back("lettuce");
sandwichMap["sauce"].push_back("mustard");
, 그리고 각 키 유형 중 하나를 사용하여 가능한 조합 (모두와 벡터를 뱉어해야한다 : 예를 단순화하기 위해, 여기에 같은 입력이 보일 수 있습니다 무엇) :
wheat+ham+lettuce+mustard
wheat+turkey+lettuce+mustard
wheat+roastbeef+lettuce+mustard
white+ham+lettuce+mustard
white+turkey+lettuce+mustard
white+roastbeef+lettuce+mustard
모든 문자열 벡터 맵에서 작동해야합니다. 지금까지 시도했지만 가까이에 있지만 중복 조합과 놓친 조합이 생깁니다.
sandwichList getCombinations(sandwichMap sMap)
{
locList retList;
int totalCombos = 1;
for (sandwichMapIt i = sMap.begin(); i != sMap.end(); ++i)
{
totalCombos *= i->second.size();
}
retList.resize(totalCombos);
int locCount;
for (sandwichMapIt a = sMap.begin(); a != sMap.end(); ++a)
{
locCount = 0;
for (locListIt l = a->second.begin(); l != a->second.end(); ++l)
{
for (unsigned int i = 0; i < totalCombos/a->second.size(); ++i)
{
retList[i + a->second.size() * locCount] += *l;
}
locCount++;
}
}
return retList;
}
어떤 도움을 주시면 감사하겠습니다!
업데이트 코드 :
#include <vector>
#include <map>
#include <list>
#include <iostream>
typedef std::vector<std::string> strVec;
typedef std::list<std::string> strList;
typedef std::map<std::string, strVec> sandwichMap;
int main()
{
sandwichMap sMap;
sMap["bread"].push_back("wheat");
sMap["bread"].push_back("white");
sMap["meat"].push_back("ham");
sMap["meat"].push_back("turkey");
sMap["meat"].push_back("roastbeef");
sMap["veggie"].push_back("lettuce");
sMap["sauce"].push_back("mustard");
strList finalSandwichList;
for (sandwichMap::iterator i = sMap.begin(); i != sMap.end(); ++i)
{
strList tmpSandwich;
for (strVec::iterator j = i->second.begin(); j != i->second.end(); ++j)
{
if (finalSandwichList.empty())
{
tmpSandwich.push_back(*j);
}
else
{
for (strList::iterator k = finalSandwichList.begin(); k != finalSandwichList.end(); ++k)
tmpSandwich.push_back(*k + "+" + *j);
}
}
tmpSandwich.swap(finalSandwichList);
}
for (strList::iterator i = finalSandwichList.begin(); i != finalSandwichList.end(); ++i)
{
std::cout << *i << std::endl;
}
return 0;
}
감사합니다! 매우 우아하고 간단한 솔루션. 나는 C++ 11이 아니기 때문에 iterator 타입 defs를 추가해야했지만 훌륭하게 작동했다. –