fork download
  1. #include <iostream>
  2. #include <iomanip>
  3. #include <algorithm>
  4. #include <string>
  5. #include <deque>
  6. #include <vector>
  7.  
  8. using std::begin;
  9. using std::end;
  10.  
  11. class NameCollection
  12. {
  13. public:
  14. typedef std::vector<std::pair<bool, std::string>> container_type;
  15.  
  16. // This is an ad hoc attempt at an iterator proxy; I wouldn't take the
  17. // iterator stuff too seriously as any sort of example code.
  18. struct const_iterator
  19. {
  20. const_iterator(container_type::const_iterator it) : _iterator(it) {}
  21.  
  22. std::string operator->() const { return _iterator->second;}
  23. std::string operator*() const { return _iterator->second;}
  24.  
  25. const_iterator& operator++() { ++_iterator; return *this;}
  26. const_iterator operator++(int) { const_iterator result(*this); ++_iterator; return result; }
  27.  
  28. bool operator==(const const_iterator& it) const { return _iterator == it._iterator;}
  29. bool operator!=(const const_iterator& it) const { return !(*this == it);}
  30.  
  31. operator container_type::const_iterator() { return _iterator; }
  32. private:
  33. container_type::const_iterator _iterator;
  34. };
  35.  
  36. friend NameCollection::const_iterator begin(const NameCollection&);
  37. friend NameCollection::const_iterator end(const NameCollection&);
  38.  
  39. std::vector<std::string> getSelected() const;
  40.  
  41. unsigned size() const {return _names.size();}
  42.  
  43. void add(const std::string& s);
  44. void select(const std::string& s);
  45. bool selected(const std::string& s) const;
  46.  
  47. void eraseSelected();
  48.  
  49. std::string operator [](unsigned index) const { return _names[index].second ; }
  50.  
  51. private:
  52.  
  53. container_type::iterator _find(const std::string& s) const
  54. {
  55. container_type & names = const_cast<container_type&>(_names); // compiler barfs if const_iterators are used. TODO: Research.
  56. return std::find_if(begin(names), end(names), [&](const container_type::value_type& value) { return value.second == s; });
  57. }
  58.  
  59. container_type _names;
  60. };
  61.  
  62. std::vector<std::string> NameCollection::getSelected() const
  63. {
  64. std::vector<std::string> selected;
  65.  
  66. for (auto & name : _names)
  67. if (name.first)
  68. selected.push_back(name.second);
  69.  
  70. return selected;
  71. }
  72.  
  73. void NameCollection::add(const std::string& s)
  74. {
  75. if (_find(s) == end(_names))
  76. _names.emplace_back(false, s);
  77. }
  78.  
  79. void NameCollection::select(const std::string& s)
  80. {
  81. auto it = _find(s);
  82.  
  83. if (it != end(_names))
  84. it->first = true;
  85. }
  86.  
  87. bool NameCollection::selected(const std::string& s) const
  88. {
  89. auto it = _find(s);
  90. return it == end(_names) ? false : it->first;
  91. }
  92.  
  93. void NameCollection::eraseSelected()
  94. {
  95. auto it = begin(_names);
  96.  
  97. while (it != end(_names))
  98. {
  99. if (it->first)
  100. it = _names.erase(it);
  101. else
  102. ++it;
  103. }
  104. }
  105.  
  106. NameCollection::const_iterator begin(const NameCollection& coll)
  107. {
  108. return begin(coll._names);
  109. }
  110.  
  111. NameCollection::const_iterator end(const NameCollection& coll)
  112. {
  113. return end(coll._names);
  114. }
  115.  
  116. void print(const NameCollection& nc, std::ostream& os = std::cout)
  117. {
  118. for (const auto name : nc)
  119. std::cout << std::setw(2) << (nc.selected(name) ? "*" : "") << ' ' << name << '\n';
  120. }
  121.  
  122. int main()
  123. {
  124. NameCollection coll;
  125.  
  126. for (char i = 'a'; i <= 'd'; ++i)
  127. {
  128. for (char j = 'a'; j <= 'd'; ++j)
  129. coll.add(std::string(1, i) + j);
  130. }
  131.  
  132. std::cout << "Original:\n";
  133. print(coll);
  134.  
  135.  
  136. for (unsigned i = 0; i < coll.size(); i += 3)
  137. coll.select(coll[i]);
  138.  
  139. std::cout << "\nAfter selection:\n";
  140. print(coll);
  141.  
  142. coll.eraseSelected();
  143.  
  144. std::cout << "\nAfter erase:\n";
  145. print(coll);
  146. }
Success #stdin #stdout 0s 3432KB
stdin
Standard input is empty
stdout
Original:
   aa
   ab
   ac
   ad
   ba
   bb
   bc
   bd
   ca
   cb
   cc
   cd
   da
   db
   dc
   dd

After selection:
 * aa
   ab
   ac
 * ad
   ba
   bb
 * bc
   bd
   ca
 * cb
   cc
   cd
 * da
   db
   dc
 * dd

After erase:
   ab
   ac
   ba
   bb
   bd
   ca
   cc
   cd
   db
   dc