#c #stl #vector
#c #stl #вектор
Вопрос:
Я все еще новичок в использовании STL. Следующий фрагмент кода заполняет 3D-вектор (Ы) и отлично компилируется (g ).
const int maxBonds = 6;
vector< vector< vector<int> > > S;
S.resize(maxBonds);
populate(S); // function that returns S with various layers filled with int data in rows and columns.
for (vector<vector<vector<int> > >::iterator Slayer = S.begin(); Slayer != S.end(); Slayer ) {
cout << "Layer contains " << Slayer->size() << " rows" << endl;
for (vector<vector<int> >::iterator Srow = Slayer->begin(); Srow != Slayer->end(); Srow ) {
for (vector<int>::iterator Scol = Srow->begin(); Scol != Srow->end(); Scol ) {
cout << *Scol;
}
cout << endl;
}
cout << endl;
}
Это выполняется нормально:
Layer contains 0 rows
Layer contains 5 rows
000
200
020
220
002
Layer contains 12 rows
100
010
210
... // etc.
Однако я хотел бы распечатать значение внешних итераторов (Slayer, Srow) во время итерации. Как мне правильно разыменовать текущее значение Slayer, т.Е.
cout << "Layer # " << Slayer->??? << " contains " << Slayer->size() << " rows" << endl;
Комментарии:
1. разве Slayer не является итератором? Разве * Slayer не работает просто?
2. @Umut — работает, но это был бы вектор, и вы не можете распечатать вектор просто так.
3. @Kiril, действительно, это вектор<vector<int> >
4. @Rolf, вы могли бы сформулировать проблему лучшим образом для дальнейшего использования, возможно, формулировка 3D-объекта с указателем на vector<вектор<int> > уменьшает уровень вложений, что-то вроде этого…
5. @Umut: попытка выполнить cout << *Slayer не работает, оператор << здесь нельзя использовать.
Ответ №1:
Если вам нужен текущий векторный «индекс», я думаю, что стандартный способ сделать это — увеличить другое значение.
unsigned int countSlayer = 0;
for (vector<vector<vector<int> > >::iterator Slayer = S.begin(); Slayer != S.end(); Slayer , countSlayer) {
cout << "Layer # " << countSlayer << " contains " << Slayer->size() << " rows" << endl;
for (vector<vector<int> >::iterator Srow = Slayer->begin(); Srow != Slayer->end(); Srow ) {
for (vector<int>::iterator Scol = Srow->begin(); Scol != Srow->end(); Scol ) {
cout << *Scol;
}
cout << endl;
}
cout << endl;
}
Вы также можете попытаться вычесть begin() из итератора, но это плохо работает со всеми типами итераторов (у меня не хватает времени на выполнение некоторых тестов).
Ответ №2:
Таким образом, *Scol
вы получаете значение int в последнем векторе, *Srow
вы получаете вектор строки, *Slayer
вы получаете вектор слоев, содержащих вектор строк.
Ответ №3:
Вы не можете сделать это напрямую.
Способ, которым я бы это сделал — определите функцию с циклом, чтобы сделать это за вас.
Что-то вроде:
void Print2dIntVector( const vector<vector<int> >amp; v )
{
// ..
}
void Print3dIntVector( const vector< vector< vector<int> > >amp; v )
{
// ..
}
Совет — используйте typedef
вместо записи всех этих длинных вложенных векторов.
РЕДАКТИРОВАТЬ: Конечно, вы всегда можете перегрузить operator<<
для этих типов (векторов)