Thread: Nested for loop...search & display a list within a list

  1. #1
    Registered User
    Join Date
    Jun 2005
    Posts
    131

    Nested for loop...search & display a list within a list

    I know how to search a list and dispaly that specific instants of the list but I don't know how to search a list with in a list and display a specific instants of the list within both lists. Hmmm did that make sense. Anyways, hear is what I have
    Code:
    {
    		string find;
    
    		cout <<"\tEnter name of Artist you want to find " << endl;
    		cout <<"\t               WARNING                " << endl;
    		cout <<"\t     THIS SEARCH IS CASE SENSITIVE    " << endl;
    		cout <<"Enter name of Artist now : " << flush;
    		cin >> find;
    		
    	list<Artist>::iterator aiter ;
    	list<CdInfo>::iterator citer ;
    		for(aiter = myArtist.begin(); aiter != myArtist.end(); iater++)
    		{
    			for(citer = myCdInfo.begin(); citer != myCdInfo.end(); citer++)
    			{
    				if ((*iter).getArtBandName() == find)
    				{
    					cout << endl << "You have just found : " << (*aiter).getArtBandName() << endl;
    				}
    			}
    		}			
    }
    My goal hear is to loop through the artist list and then search for the CD that goes with that artist. Then I want to be able to display that information back to the user. For example, the user enters the artist name AAAA. The program searches for AAAA and displays AAAA and the CD that goes with AAAA. If you need more information tell me. Any advice would help.

    Thanks

  2. #2
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    Why do you have two seperate lists? Why don't you just have one list that contains all the information you need? I don't really see the point of having seperate lists.
    Code:
    for each item in the big list
        if this item matches whatever it is you're looking for
            display it
    It's pretty simple stuff.

    Other than that, since we have no idea what your lists look like, or what they contain, it's not really easy to give you an answer. Still, I don't see the point of two seperate lists, other than to make more work for yourself.


    Quzah.
    Hope is the first step on the road to disappointment.

  3. #3
    Registered User
    Join Date
    Jun 2005
    Posts
    131
    I have two seperate list because I am first asking the user to enter a CD name and then an Artist name. Let me see if I can show you. This is part of my Artist class
    Code:
    //Holds artName
    void Artist::setArtBandName(string lv_artName) 
    { 
    artName = lv_artName; 
    } 
    
    string Artist::getArtBandName() 
    { 
    return artName; 
    }
    
    
    //Adds Cd Name
    void Artist::AddCdName()
    {
    	string cdName; 
    
    		cout << "Enter Cd's Name:" << flush; 
    		cin >> cdName; 
    	
    		myCdInfo.push_back(CdInfo(cdName));	
    
    		cout << "\tAdded : " << cdName << endl << endl;		
    	OptionArtistInfo();
    }
    
    //Display Cd List
    void Artist::DisplayCdList()
    {
    		cout << endl << "Cd List:" << endl;
      
    	list<CdInfo>::iterator iter;
    
    		for(iter = myCdInfo.begin(); iter != myCdInfo.end(); iter++)
    		{
    			cout << (*iter).getCdName();		
    		}
    }
    
    void Artist::OptionArtistInfo()
    {
    	 int input;
    
    	//A do while loop might be needed 
    			cout << "Would you like to add Artist info for the cd : " << endl; 
    			cout << "\tType 1 for yes or 2 for no : " << flush;
    			cin >> input;
    		
    			switch (input)
    			{
    			case 1:
    					cout << endl << "Enter the bands name: " << flush; 
    					cin >> artName; 
    				break;
    			case 2:
    				cout << "Returning to main menu" << endl;
    				break;
    			default:
    				cout << input << " : Is not a valid command" << endl;
    				cout << " 1 and 2 are valid commands " << endl;
    			}
    }
    This is part of my controller class
    Code:
    //********************ARTIST**********************
    
    //Adds Artist Name
    void Controller::AddArtBandName() 
    { 
    	string artName; 
    
    		cout << endl << "Enter the bands name: " << flush; 
    		cin >> artName; 
    
    		myArtist.push_back(Artist(artName));	
    		
    		cout << "\tAdded : " << artName << endl << endl ;		
    } 
    void Controller::FindCd()
    {
    		string find;
    
    		cout <<"\tEnter name of Artist you want to find " << endl;
    		cout <<"\t               WARNING                " << endl;
    		cout <<"\t     THIS SEARCH IS CASE SENSITIVE    " << endl;
    		cout <<"Enter name of Artist now : " << flush;
    		cin >> find;
    		
    	list<Artist>::iterator aiter ;
    	list<CdInfo>::iterator citer ;
    		for(aiter = myArtist.begin(); aiter != myArtist.end(); aiter++)
    		{
    			for(citer = myCdInfo.begin(); citer != myCdInfo.end(); citer++)
    			{
    				if ((*aiter).getArtBandName() == find)
    				{
    					cout << endl << "You have just found : " << (*aiter).getArtBandName() << endl;
    				}
    			}
    		}			
    }

  4. #4
    Banned
    Join Date
    Jun 2005
    Posts
    594
    you still dont need two lists

  5. #5
    Registered User
    Join Date
    Jun 2005
    Posts
    131
    Quote Originally Posted by ILoveVectors
    you still dont need two lists
    Why is that. I thought the only way to treat two diffrent inputs from the user as two diffrent varaibles but still have them linked in some way when using a list is through a list with in a list.

  6. #6
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    You don't need two lists, but it is ok if you have them. The key is using them correctly.

    I'm not sure what happened since the last time I saw your findCd function, but it seems to have gone backwards. There are a number of ways to do these things, so you have to try to understand the advice of each person and determine which way you want to do it. You're going to get a lot of conflicting advice, which is ok if you understand what people are saying and what you're doing.

    The last time I saw your findCd function, I was recommending that you have a findCd function in the Controller and one in the Artist. The one in the Controller would loop through the list of Artists and call the findCd function for each Artist. The function in the Artist would loop through its own Cd list and find the appropriate Cd, returning true if it was found. In that setup, you had only one list in the Controller - the list of Artists - and you had a list of CdInfos in each Artist instead of a master list in the Controller. Is there a reason you changed that?

  7. #7
    Registered User
    Join Date
    Jun 2005
    Posts
    131
    Quote Originally Posted by Daved
    You don't need two lists, but it is ok if you have them. The key is using them correctly.

    I'm not sure what happened since the last time I saw your findCd function, but it seems to have gone backwards. There are a number of ways to do these things, so you have to try to understand the advice of each person and determine which way you want to do it. You're going to get a lot of conflicting advice, which is ok if you understand what people are saying and what you're doing.

    The last time I saw your findCd function, I was recommending that you have a findCd function in the Controller and one in the Artist. The one in the Controller would loop through the list of Artists and call the findCd function for each Artist. The function in the Artist would loop through its own Cd list and find the appropriate Cd, returning true if it was found. In that setup, you had only one list in the Controller - the list of Artists - and you had a list of CdInfos in each Artist instead of a master list in the Controller. Is there a reason you changed that?
    Well in regards to your first paragraph I understand your point. There has been many conflicting ideas as to what is correct and what is not. I always try to get people to explain themselves because I want to be able to make the choice myself based on other peoples opinions. Since I have started posting hear I have learned a bunch of new stuffed and at the same time realized there is plenty more to learn.

    As to why I changed my approach at this. It is because of others conflicting opinions as to what I should do. To be honest this has been one of the harder things for me to figure. Everyone tells me it should be easy and by looking at the rest of my program I should be able to figure it out nice and quick. If only that were the truth. Since I last talked to you I have went over this numerus times. For some reason it just is not clicking in my head. I am sure once I finally figure it out I will realize just how easy it was.

    Thanks

    Chad

  8. #8
    Banned
    Join Date
    Jun 2005
    Posts
    594
    maybe this would be a more favorable solution ?

    Code:
    #include <iostream>
    #include <string>
    #include <map>
    #include <utility>
    
    using namespace std;
    
    int main()
    {
    	string cdname = "Hypnotica";
    	string songname = "Benny Benassi - Satisfaction";
    	map<string, string> band;
    	band[cdname] = songname;
    	map<string, string>::const_iterator it;
                    for (it = band.begin(); it != band.end(); ++it)
    	{
                            cout << it->first << " = " << it->second << endl;
                    }
    	cin.get();
    	return 0;
    }
    more info on maps:

    http://www.cppreference.com/cppmap/

    http://cplus.about.com/od/stltutorial/l/aa120103e.htm

  9. #9
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    ILoveVectors, one problem with your solution is that each cd would only contain one song. Beyond that, chadsxe has an existing hierarchy of code that attempts to encapsulate the separate notions of an Artist, a CD, a Controller, etc. A map might be appropriate, but I don't think chadsxe should completely re-write all the code to use it.

    Here is my suggested pseudo-code:

    Controller::Menu()
    -- If option 3 is selected call the function FindCd() that is part of the Controller class.

    void Controller::FindCd()
    -- Prompt the user to enter a CdName.
    -- Store this name in a string.
    -- Create a bool variable initialized to false that will store whether any match was found.
    -- Loop through each Artist in the Controller's Artist list. For each one do the following:
    -- -- Call the FindCd function for the Artist. Pass the string received from the user and check the return value. For example:
    Code:
    bool found = (*aiter).FindCd(input);
    -- -- If found is true, output the name of the Artist using getArtBandName and the name of the Cd from the input string. Set the bool variable for any match to true.
    -- End loop
    -- If the bool variable that holds any match is false, output an error message saying no Cd was found.

    bool Artist::FindCd(string input)
    -- Take a string as an argument and return a bool.
    -- Loop through each Cd in the list of Cds stored in the artist. For each one do the following:
    -- -- Compare the name of the Cd to the passed in input string.
    -- -- If the names match, return true.
    -- End Loop
    -- If the loop ends, then return false, the Cd name was not found.

    Hope that makes sense.

  10. #10
    Banned
    Join Date
    Jun 2005
    Posts
    594
    really i thought you could just
    keep the cd and song as
    a string for the entirty of
    all the songs, then just use
    a new cd name, then they would be
    one after another in the map like so

    Code:
    CD NAME1 , SONG NAME1
    CD NAME1 , SONG NAME2
    CD NAME1 , SONG NAME3
    CD NAME1 , SONG NAME4
    CD NAME1 , SONG NAME5
    CD NAME1 , SONG NAME6
    CD NAME1 , SONG NAME7
    CD NAME1 , SONG NAME8
    CD NAME1 , SONG NAME9
    CD NAME1 , SONG NAME10
    CD NAME1 , SONG NAME11
    CD NAME1 , SONG NAME12
    CD NAME1 , SONG NAME13
    CD NAME2 , SONG NAME1
    CD NAME2 , SONG NAME2
    CD NAME2 , SONG NAME3
    CD NAME2 , SONG NAME4
    CD NAME2 , SONG NAME5
    CD NAME2 , SONG NAME6
    CD NAME2 , SONG NAME7
    CD NAME2 , SONG NAME8
    CD NAME2 , SONG NAME9
    CD NAME2 , SONG NAME10
    CD NAME2 , SONG NAME11
    CD NAME2 , SONG NAME12
    i suppose they could do it
    liek this

    Code:
    BAND/ARTISTNAME , ALBUM - SONG NAME

  11. #11
    Banned
    Join Date
    Jun 2005
    Posts
    594
    or you could simply use a vector<string>


    put all the info together in one string all lowercase,
    then get a search criteria, and search each string for
    the criteria.
    such as

    Code:
    band/artistname|albumname|tracknumber|songname
    but im still not seeing why the list is becomming
    so complicated, maybe ill work on some list code,
    and see if i can come up with a easy solution.

  12. #12
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    The original problem with your map was that it doesn't hold duplicate keys, so only one entry per cdname would be allowed. A multimap would be better.

    However, it is a better idea, IMO, for chadsxe to continue to keep each item encapsulated in its own object, and provide appropriate interfaces for each object. For example, a CdInfo class that contains the information for a specific CD. Then, an Artist class that contains an Artist and a list of all CDs from that Artist. Then, a Controller class that has a list of all Artists in the database. I agree that there might be better ways to solve this than these lists, but I think it would be more important for chadsxe to get the current code working and then make optimizations later, especially if those optimizations involve learning new topics (like maps or dynamic memory).

  13. #13
    Banned
    Join Date
    Jun 2005
    Posts
    594
    yea i woudl agree to fix the original code, before learning
    something new, it was just an idea, i am always trying
    to think of a faster way to get it done, but now that i look
    deeper my way may not nessassarily be faster and may
    acctually be harder then what i originally thought.

  14. #14
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    Why don't you just make a CD class that contains the following:
    a) The name of the CD.
    b) The name of the artist.
    c) A list of songs.

    Now all you do when you read in a song is find out what CD it goes to, and add it to that list.

    Want to find an artist? Simply loop through the CD list. Want to find all of the songs by an artist? Loop through your CD list, and if the artist matches, assuming you want to do so, display all of the songs for this CD.


    Quzah.
    Hope is the first step on the road to disappointment.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. problem with structures and linked list
    By Gkitty in forum C Programming
    Replies: 6
    Last Post: 12-12-2002, 06:40 PM
  2. List class
    By SilasP in forum C++ Programming
    Replies: 0
    Last Post: 02-10-2002, 05:20 PM
  3. Linked list with two class types within template.
    By SilasP in forum C++ Programming
    Replies: 3
    Last Post: 02-09-2002, 06:13 AM
  4. singly linked list
    By clarinetster in forum C Programming
    Replies: 2
    Last Post: 08-26-2001, 10:21 PM