С++ STL Vector Iterator, получающий доступ к элементам объекта

Я думаю, что я правильно объявил вектор с объектом. Но, я не знаю, как получить доступ к ним при циклировании с помощью Iterator.

В моем коде строка --- → cout < "" < * Iter;

Как распечатать содержимое участников? Как * Iter.m_PackLine???

Не уверен, что я использовал правильную терминологию, но ценю помощь! Благодаря

class CFileInfo
{
  public:
      std::string m_PackLine;
      std::string m_FileDateTime;
      int m_NumDownloads;
};

void main()
{
  CFileInfo packInfo;

  vector<CFileInfo, CFileInfo&> unsortedFiles;
  vector<CFileInfo, CFileInfo&>::iterator Iter;

  packInfo.m_PackLine = "Sample Line 1";
  packInfo.m_FileDateTime = "06/22/2008 04:34";
  packInfo.m_NumDownloads = 0;
  unsortedFiles.push_back(packInfo);

  packInfo.m_PackLine = "Sample Line 2";
  packInfo.m_FileDateTime = "12/05/2007 14:54";
  packInfo.m_NumDownloads = 1;
  unsortedFiles.push_back(packInfo);

 for (Iter = unsortedFiles.begin(); Iter != unsortedFiles.end(); Iter++ )
 {
    cout << " " << *Iter; // !!! THIS IS WHERE I GET STUMPED
    // How do I output values of the object members? 
 }
}  // end main

Ответ 1

cout << " " << *Iter;

будет работать, только если CFileInfo имеет перегруженный operator<<, который может выводить вашу структуру. Вы можете выводить отдельные элементы структуры, а именно:

cout << " " << Iter->m_PackLine;

В качестве альтернативы, это эквивалентно следующему:

cout << " " << (*Iter).m_PackLine;

Вы должны помещать круглые скобки вокруг * Iter, так как оператор доступа к члену привязывает в противном случае в противном случае.

На стороне node сделайте свою основную функцию возвратом int вместо void. что он возвращает void, недействителен в С++.


Вы объявляете вектор следующим образом:

vector<CFileInfo, CFileInfo&> unsortedFiles;

Второй аргумент vector должен быть другой. Для вашего кода не требуется, чтобы вектор был вторым аргументом. Просто используйте это:

vector<CFileInfo> unsortedFiles;

Еще одна вещь, которую я заметил, - это увеличить итератор с помощью Iter++ (называемый postfix increment). Для итераторов всегда предпочитайте ++Iter, который называется prefix increment.

Ответ 2

Используйте (* iter).member или iter- > member.

Вы также можете использовать временные файлы:

CFileInfo &fileInfo = *iter;
cout << " " << fileInfo.myMember;

Кроме того, для того, что вы делаете, вам, вероятно, понадобится const_iterator вместо (изменяемого) итератора.

Кроме того, std::vector является шаблоном, принимающим имя и распределитель, а не два типа имен. Вы можете использовать распределитель по умолчанию, разделив второй аргумент шаблона:

vector<CFileInfo> unsortedFiles;
vector<CFileInfo>::iterator Iter;

Некоторые nit-picking:

  • main должен возвращать int.
  • Вероятно, было бы лучше объявить переменную iterator в инструкции for.
  • Вероятно, быстрее во время выполнения использовать оператор prefix ++ (++ iter) вместо оператора postfix (iter ++) в вашем цикле for.
  • Нет необходимости в комментариях о завершении main().

Ответ 3

Это первая проблема, которую я заметил:

std::vector является шаблоном.

У вас есть:

vector unsortedFiles;

вам нужно что-то вроде:

vector<CFileInfo> unsortedFiles;

Теперь, когда я думаю об этом, ваше определение шаблона может быть просто обработано системой комментариев stackoverflow.

Ответ 4

Сначала исправьте векторное объявление:

vector<CFileInfo > unsortedFiles;

Далее вам нужно определить оператор вывода для вашего класса:

std::ostream& operator<<(std::ostream& str,CFileInfo const& data)
{
       // Do something here
       /* Potentailly you could do this
        *    But this requires that this function be a friend of the class

       str << data.m_PackLine << ":"
           << data.m_FileDateTime << ":"
           << data.m_NumDownloads << ":";

       *  Or you could do this

           data.print(str);  // Make print a public const method.

       */

       return str;
}

Обычно вы либо делаете оператор вывода другом своего класса, либо предоставляете публичный метод печати, который принимает поток. В любом случае вы можете получить доступ к элементам и передать их вручную на выход.

После того, как вы определили выходной итератор, вы можете изменить свой цикл, чтобы использовать стандартные версии библиотеки:

std::for_each(unsortedFiles.begin()
              unsortedFiles.end()
              std::ostream_iterator<CFileInfo>(std::cout," ")
             );

Ответ 5

iter->m_PackLine

или

(*iter).m_PackLine

Ответ 6

vector<CFileInfo, CFileInfo& > вообще не работает. Второй параметр для вектора - это распределитель, который использует вектор, а CFileInfo не отвечает этим требованиям и не имеет никакого ссылочного типа. Я думаю, вам просто нужно vector<CFileInfo>, итераторы и члены возвратят CFileInfo& автоматически.

Ответ 7

Спасибо, желаю, чтобы я мог предоставить несколько баллов за ответы:)

litb также указал на проблему, которую я имел в своем объявлении вектора. Я удалил второй аргумент в объявлении вектора, и он сработал.

Stackoverflow проанализировал часть моего кода, я буду более осторожен при публикации в следующий раз.