Я больше привык к одной карте, а не к вложенной карте. Поэтому у меня есть серьезные трудности с пониманием, как с этим справиться.
Примечание: Пожалуйста, не просите меня использовать мультикарту или повышение, я ограничен в использовании этой структуры
В C ++ STL map у меня есть такое определение
map<string, map<string, string>> exploration; // country --> state --> city
Первая карта представляет пару ключей (страна) и значение в виде древовидной структуры map<string, string>
которые представляют там соответствующий штат и город.
Я знаю, как заполнить эту структуру вручную (жесткое кодирование) вот так:
exploration["Canada"]["Ontario"] = "Toronto";
Проблема:
Позже показанные выше данные будут введены пользователем:
> Canada Ontario Toronto
> Canada Alberta Edmonton
> USA Washington Seatle
> USA Nevada Las-Vegas
Так что если я применяю эту логику к моему примеру выше, это неправильно, так как карта не принимает дубликаты ключей
иллюстрация (неправильно) :
exploration["Canada"]["Ontario"] = "Toronto";
exploration["Canada"]["Alberta"] = "Edmonton";
иллюстрация (Что я ищу) :
exploration["Canada"]["Ontario"] = "Toronto";
["Alberta"] = "Edmonton";
Canada
**
* *
* *
Ontario Alberta
* *
* *
Toronto Edmonton
Мое гипотетическое решение,
> Canada Ontario Toronto
1 случай: Если страна (Канада) не существует в структуре разведки, я добавляю ее, а также провинцию и ее город.
2 случая: Если страна (Канада) существует, то я добавлю Онтарио и Торонто длинной стороной к данным, введенным ранее.
Любые указания, идеи или советы приветствуются.
Ваш пример совершенно прав. Глядя на код ниже (в C ++ 11, но те же рассуждения применимы к предыдущим версиям), вы можете видеть, что каждая страна вставляется только один раз в exploration
карта.
Код:
#include <iostream>
#include <map>
using namespace std;
int main() {
map<string, map <string, string> > exploration;
exploration["Canada"]["Ontario"] = "Toronto";
exploration["Canada"]["Alberta"] = "Edmonton";
exploration["USA"]["Washington"] = "Seattle";
exploration["USA"]["Nevada"] = "Las Vegas";
cout << "Number of keys: " << exploration.size() << endl;
for (auto country : exploration) {
for (auto city : country.second)
cout << country.first << ":" << city.first << " -> " << city.second << endl;
}
return 0;
}
Выход:
Number of keys: 2
Canada:Alberta -> Edmonton
Canada:Ontario -> Toronto
USA:Nevada -> Las Vegas
USA:Washington -> Seattle
Давайте шаг за шагом поймем, что происходит:
map<string, map <string, string> > exploration
: Определяет карту, ключи которой являются строками, а ее значения — другими картами. Пока пусто.exploration["Canada"]["Ontario"] = "Toronto"
: Сначала это проверяет Canada
не существует в exploration map
, Следовательно, создается сопоставление Canada
на пустую карту. Теперь отображение из Ontario
в Toronto
создается внутри exploration["Canada"]
карта.exploration["Canada"]["Alberta"] = "Edmonton"
: С Canada
ключ уже существует в exploration
Нет необходимости создавать его снова. Это будет просто карта Alberta
в Edmonton
в уже созданной карте.То же самое относится и к USA
карта. Таким образом, не будет дублированных ключей даже с вложенными картами. С ++ великолепен.
Вы можете иметь два города в одном штате, так что вам действительно нужно map<string, map<string, set<string>>>
Но то, что у вас есть до этого, уже будет работать. Например:
#include <iostream>
#include <map>
#include <set>
#include <string>
int main() {
std::map<std::string, std::map<std::string, std::set<std::string>>> countries;
countries["Canada"]["Ontario"].insert("Toronto");
countries["Canada"]["Ontario"].insert("Something else");
countries["Canada"]["Alberta"].insert("Edmonton");for (const auto& country : countries) {
std::cout << "Country: " << country.first << "\n";
for (const auto& statePair : country.second) {
std::cout << "State: " << statePair.first << "\n";
for (const auto& city : statePair.second) {
std::cout << "City: " << city << "\n";
}
}
}
return 0;
}
Будет выходной
Country: Canada
State: Alberta
City: Edmonton
State: Ontario
City: Something else
City: Toronto
РЕДАКТИРОВАТЬ:
Что касается вашего последующего вопроса, это должно привести вас туда:
using CountryMap = std::map<std::string, std::map<std::string, std::set<std::string>>>;
bool countryContainsCity(const CountryMap& countryMap, const std::string& country, const std::string& city)
{
for (const auto& country : countryMap[country]) {
for (const auto& statePair : country.second) {
if (statePair.second.find(city)
{
return true;
}
}
}
return false;
}