Thread: STL algorithms

  1. #1
    Cheesy Poofs! PJYelton's Avatar
    Join Date
    Sep 2002
    Location
    Boulder
    Posts
    1,728

    STL algorithms

    Hey everyone, I'm currently trying to self teach myself most of the STL algorithms and have come across a weird error - or if it isn't an error then I'm VERY confused! It involves the algorithms unique and remove using MSVC++, which do as they advertise BUT when they take out numbers in a container, they don't shorten the container length! Like so:
    Code:
    #include<iostream>
    #include<vector>
    #include<algorithm>
    using namespace std;
    
    void displayVec(vector<int> vec)
    {
    	for (int x=0; x<vec.size(); x++)
    		cout<<vec[x]<<" ";
    	cout<<endl;
    }
    
    void initializeVec(vector<int>& vec)
    {
    	while(vec.size())
    		vec.pop_back();
    
    	vec.push_back(3);
    	vec.push_back(7);
    	vec.push_back(3);
    	vec.push_back(3);
    	vec.push_back(9);
    	vec.push_back(4);
    	vec.push_back(1);
    	vec.push_back(2);
    }
    
    int main()
    {
    	vector<int> vec;
    
    	initializeVec(vec);
    	cout<<"Before unique: ";
    	displayVec(vec);
    
    	unique(vec.begin(), vec.end());
    	cout<<"After unique:  ";
    	displayVec(vec);
    
    	initializeVec(vec);
    	cout<<"Before remove: ";
    	displayVec(vec);
    
    	remove(vec.begin(), vec.end(), 3);
    	cout<<"After remove:  ";
    	displayVec(vec);
    
    	return 0;
    }
    Here is the output:
    Code:
    Before unique: 3 7 3 3 9 4 1 2
    After unique:  3 7 3 9 4 1 2 2
    Before remove: 3 7 3 3 9 4 1 2
    After remove:  7 9 4 1 2 4 1 2
    Press any key to continue
    It removed the numbers as advertised, and shifted the later numbers to the left also as advertised, but it didn't delete the end or shorten the vector size. Is this supposed to happen? And if so, then of what use are these two algorithms?

  2. #2
    &TH of undefined behavior Fordy's Avatar
    Join Date
    Aug 2001
    Posts
    5,793
    Remember that the stl algorithms are largely generic, and try not to make many assumptions on the container you are using.....

    In this case, it removes the values but doesnt shorten the vector....to do so;

    Code:
    #include<iostream>
    #include<vector>
    #include<algorithm>
    using namespace std;
    
    void displayVec(const vector<int>& vec)//pass by const ref!!!
    {
    	for (int x=0; x<vec.size(); x++)
    		cout<<vec[x]<<" ";
    		cout<<endl;
    }
    
    void initializeVec(vector<int>& vec)
    {
    	vec.clear();//use clear!!!
    	
    	vec.push_back(3);
    	vec.push_back(7);
    	vec.push_back(3);
    	vec.push_back(3);
    	vec.push_back(9);
    	vec.push_back(4);
    	vec.push_back(1);
    	vec.push_back(2);
    }
    
    int main()
    {
    	vector<int> vec;
    
    	initializeVec(vec);
    	cout<<"Before unique: ";
    	displayVec(vec);
    
    	vec.erase(unique(vec.begin(), vec.end()),vec.end());//erase!!
    	cout<<"After unique:  ";
    	displayVec(vec);
    
    	initializeVec(vec);
    	cout<<"Before remove: ";
    	displayVec(vec);
    
    	vec.erase(remove(vec.begin(), vec.end(), 3),vec.end());//erase!!
    	cout<<"After remove:  ";
    	displayVec(vec);
    
    }

  3. #3
    CALVIN
    Guest

    unique() & remove()

    unique() and remove() return a forward iterator indicating the new end position.

    try this,

    Code:
    #include<iostream>
    #include<vector>
    #include<algorithm>
    
    using namespace std;
    
    void displayVec(vector<int>& vec, vector<int>::iterator end_it)
    {
            vector<int>::iterator tmp_it;
    
    	for (tmp_it = vec.begin(); tmp_it != end_it; tmp_it++)
    		cout<<*tmp_it<<" ";
    
    	cout<<endl;
    }
    
    void initializeVec(vector<int>& vec)
    {
            vec.clear();
    
    	vec.push_back(3);
    	vec.push_back(7);
    	vec.push_back(3);
    	vec.push_back(3);
    	vec.push_back(9);
    	vec.push_back(4);
    	vec.push_back(1);
    	vec.push_back(2);
    }
    
    int main()
    {
    	vector<int> vec;
    
    	initializeVec(vec);
    	cout<<"Before unique: ";
    	displayVec(vec, vec.end());
    
    	cout<<"After unique:  ";
    	displayVec(vec, unique(vec.begin(), vec.end()));
    
    	initializeVec(vec);
    	cout<<"Before remove: ";
    	displayVec(vec, vec.end());
    
    	cout<<"After remove:  ";
    	displayVec(vec, remove(vec.begin(), vec.end(), 3));
    
    	return 0;
    }

  4. #4
    Cheesy Poofs! PJYelton's Avatar
    Join Date
    Sep 2002
    Location
    Boulder
    Posts
    1,728
    Okay, that makes more sense although and I understand now how to get around it, but I'm still dumbfounded as to why the STL creators didn't make popping the back of the container automatic with unique and remove. I can't think of a reason why someone WOULDN't want this done, although is somebody knows I would love to be told!

    Thanks for pointing out the member function clear(), I haven't gotten to many of the member functions yet and that is definately a useful one! And as far as the constant reference, I usually do, just didn't this time because I was in a hurry to make this post and I forgot

  5. #5
    &TH of undefined behavior Fordy's Avatar
    Join Date
    Aug 2001
    Posts
    5,793
    Originally posted by PJYelton
    Okay, that makes more sense although and I understand now how to get around it, but I'm still dumbfounded as to why the STL creators didn't make popping the back of the container automatic with unique and remove. I can't think of a reason why someone WOULDN't want this done, although is somebody knows I would love to be told!

    Thanks for pointing out the member function clear(), I haven't gotten to many of the member functions yet and that is definately a useful one! And as far as the constant reference, I usually do, just didn't this time because I was in a hurry to make this post and I forgot :D
    The reason why is simple - flexability.......Look at this

    Code:
    #include <iostream>
    #include <vector>
    #include <algorithm>
    
    
                        
    int main(void){
    	
    
    	int Arr[] = {3,2,4,5,3,1,2,3};//My array
    	
    	//print array
    	copy(Arr,Arr+sizeof(Arr)/sizeof(Arr[0]),std::ostream_iterator<int>(std::cout, " "));
    	
    	std::remove(Arr,Arr+sizeof(Arr)/sizeof(Arr[0]),3);//remove 3
    	
    	std::cout << std::endl;
    	
    	//print array
    	copy(Arr,Arr+sizeof(Arr)/sizeof(Arr[0]),std::ostream_iterator<int>(std::cout, " "));
    	
    	
    }
    2 STL algorithms but using a std C typr array....

    The reason why I can do this is that the algorithm doesnt care about the data struct......why should it? - it treats an iterator for a container just as an array, and so I can use any container I wish....but the trade off is that the algorithm doesnt know if the container is a true object, or what member functions it may have.......that's why it doesnt delete at the end.....it cant do so with arrays, so it cant do so ever

  6. #6
    Cheesy Poofs! PJYelton's Avatar
    Join Date
    Sep 2002
    Location
    Boulder
    Posts
    1,728
    Thanks for the help fordy! That makes a whole lot of sense now! The STL book I'm using doesn't go into any explanation, just heres the algorithm, this is what it does, next algorithm...

  7. #7
    &TH of undefined behavior Fordy's Avatar
    Join Date
    Aug 2001
    Posts
    5,793
    Originally posted by PJYelton
    Thanks for the help fordy! That makes a whole lot of sense now! The STL book I'm using doesn't go into any explanation, just heres the algorithm, this is what it does, next algorithm...
    A good book - The Standard C++ Library by Josuttis......that one does take the time to discuss why as well as how

  8. #8
    Cheesy Poofs! PJYelton's Avatar
    Join Date
    Sep 2002
    Location
    Boulder
    Posts
    1,728
    Cool, I'll keep that book in mind for when I actually have money to spare - tis why I'm using such a crappy book, its from the local library

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. removing whitspaces with STL algorithms
    By Micko in forum C++ Programming
    Replies: 2
    Last Post: 06-03-2006, 01:48 AM
  2. C Formatting Using STL
    By ChadJohnson in forum C++ Programming
    Replies: 4
    Last Post: 11-18-2004, 05:52 PM
  3. im extreamly new help
    By rigo305 in forum C++ Programming
    Replies: 27
    Last Post: 04-23-2004, 11:22 PM
  4. Prime Number Generator... Help !?!!
    By Halo in forum C++ Programming
    Replies: 9
    Last Post: 10-20-2003, 07:26 PM
  5. include question
    By Wanted420 in forum C++ Programming
    Replies: 8
    Last Post: 10-17-2003, 03:49 AM