Вы можете сделать одну из четырех вещей:
1) Используйте готовое ключевое слово auto, как уже отвечено.
2) Дайте контейнеру typedef общее имя, чтобы вы могли изменить его тип, не желая переписывать его общее использование.
typedef std::vector<config_value_ptr> config_value_container;
config_value_container config;
config_value_container::iterator it = config.begin();
3) Если вы хотите, чтобы имя контейнера typedef оставалось конкретным, вы можете сделать итератор typedef.
typedef std::vector<config_value_ptr> config_value_vec;
typedef config_value_vec::iterator config_value_container_iterator;
config_value_vec config;
config_value_container_iterator it = config.begin();
Конечно, если вы начинаете нуждаться в разных типах итераторов для контейнера (const против non-const, backward vs forward и т. Д.), То вы можете получить несколько итераторов typedef.
4) Не беспокойтесь об этом, потому что типы контейнеров могут иметь фундаментальные различия, которые вы, возможно, не сможете устранить с помощью простых определений типов. Например, std :: sort можно использовать с std :: vector, но не с std :: list. В зависимости от того, что делает ваш код (или может понадобиться в будущем), попытка сохранить его по-настоящему независимым от типа может занять больше времени, чем оно того стоит. Но вам придется оценить это самостоятельно.