Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

Background I have a music player on my phone. I can buy songs, add them to playl

ID: 3705696 • Letter: B

Question

Background

I have a music player on my phone. I can buy songs, add them to playlists and play them. Obviously it would be redundant to store each song in each playlist; each playlist is just a list of pointers to the songs.

For this lab you will simulate this behavior. Your program will need to have options to:

Add songs to the system library (you will store the text of the first line of the song, rather than the audio)

Add playlists

Add songs to a playlist

List playlists

Play a playlist

List all of the songs in the library with a count of how many times each song has been played

Delete a song from a playlist

Delete a playlist

Delete a song from the library (and thus from all playlists that contain it)

Note that we will not be checking many error cases. In real programming this would be bad, you should usually try to recognize and respond to as many types of errors as you can. In the context of class we are trying to acquaint you with as many concepts as possible, so for the sake of educational efficiency we will not be checking most errors in this lab, you may assume that your user provides correct input. You may add all appropriate error testing if you wish, but we will not be testing for it.

Requirements

This lab must be done individually; not with pair programming. See the example below to see the expected formatting.

Part 1 - The Menu (10 points)

Prompt the user to select one of several operations:

After any operation is complete (except for quitting), re-prompt the user to select another operation. If the user enters an unknown option, just print the menu. For part 1, only the quit and options option need work.

Part 2 - Add and display songs (25 points)

For this part you will need to create a song class and vector of pointers to songs. This will be your library of songs.

As songs are added use "new".

At the end of your program free the space for each song using "delete".

Add songs

Prompt the user for the name of the song (you do not need to check for duplicate names).

Prompt the user for the first line of the song.

Initialize the count of how many times this song has been played to 0.

Continue to prompt for songs until the user responds with "STOP".

List all songs - display a list of all of the songs currently in the system and the number of times each song has been played.

Part 3 - Playlists (40 points)

For this part you will need to create a playlist class and a vector of playlists.

Add a playlist

Prompt the user for the name of the playlist (you do not need to check for duplicate names).

Add the new playlist to the vector of playlists.

List a playlist

Add a song to a playlist

List all of the playlists currently in the system and let the user select one of them.

List all of the songs currently in the system and let the user select one of them.

Add a pointer to the selected song into the selected playlist.

Play playlist

List all of the playlist names and let the user select one of them.

"Play" the songs in the play list by printing their first lines.

Whenever a song is played from any playlist, add to the count of how many times it has been played. Note that this is the number of times it has been played, not the number of playlists it is on.

Verify that when you use the "list all songs" operation that the correct count is displayed.

Part 4 - Delete songs and playlists (25 points)

Delete a playlist

Delete a song from a playlist

Note that this does not delete the song from the library

Delete a song from the library. Think about this one!

You will need to first delete the song from any playlist which contains it

You must free the memory that the song object was allocated to (c++ delete)

Then erase it from the library

Deductions graded by TA's

You must create and use a Song class and a PlayList class. (10 points)

You must create and use a vector of Song pointers as the music library. (10 points)

Your playList class must contain and use a vector Song pointers. (10 points)

You must create the class declarations and definitions in separate files as instructed. (10 points)

Always create your own default constructor for each class, and create a parameterized constructor(s) as required. You may combine these into one constructor function by creating a default constructor with default parameters. (5 points each)

You must use new to create your songs and free memory (delete) for any song which you delete from the library, and all songs after you quit the program. If you use pointers for playlists you must also free memory when playlists are deleted. To help the TAs, place a comment about freeing memory next to the lines in your code which free memory, and in your header give the file and line numbers of those lines. (10 points)

Sample Input

Sample Output Visual Studio View

Explanation / Answer

Solution:

The Complete C++ code for given problem is shown below:

Song.h

//Include libraries

#ifndef SONG_H

#define SONG_H

#include <string>

//Use namespace

using namespace std;

//Define class

class Song

{

     //Define access specifier

     public:

     //Define constructor

     Song();

     //Define constructor

     Song(string songName, string firstLine, int yearOfSong);

     //Define method

     string GetSongName() const;

     //Define method

     string GetFirstLine() const;

     //Define method

     int GetTimesPlayed() const;

     //Define method

     int GetYear() const;

     //Define method

     void PrintSongInfo() const;

     //Define method

     void IncrementPlayCount();

     //Define method

     void PlaySong();

     //Define access specifier

     private:

     //Declare variable

     string songName;

     //Declare variable

     string firstLine;

     //Declare variable

     int yearOfSong;

     //Declare variable

     int numTimesPlayed;

};

//End

#endif

Song.cpp

//Include libraries

#include <iostream>

#include <string>

#include "Song.h"

//Use namespace

using namespace std;

//Define constructor

Song::Song()

{

     //Set value

     this->songName = "none";

     //Set value

     this->firstLine = "none";

     //Set value

     this->yearOfSong = 0;

     //Set value

     this->numTimesPlayed = 0;

}

//Define constructor

Song::Song(string songName, string firstLine, int yearOfSong)

{

     //Set value

     this->songName = songName;

     //Set value

     this->firstLine = firstLine;

     //Set value

     this->yearOfSong = yearOfSong;

     //Set value

     this->numTimesPlayed = 0;

}

//Define method

string Song::GetSongName() const

{

     //Return

     return this->songName;

}

//Define method

string Song::GetFirstLine() const

{

     //Return

     return this->firstLine;

}

//Define method

int Song::GetTimesPlayed() const

{

     //Return

     return this->numTimesPlayed;

}

//Define method

int Song::GetYear() const

{

     //Return

     return this->yearOfSong;

}

//Define method

void Song::PrintSongInfo() const

{

     //Display message

     cout << "Name: "" << GetSongName() << "" FirstLine: "" << GetFirstLine() << """;

     //Display message

     cout << " Released in: " << GetYear() << " Played " << GetTimesPlayed() << " times." << endl;

}

//Define method

void Song::IncrementPlayCount()

{

     //Increment

     this->numTimesPlayed++;

}

//Define method

void Song::PlaySong()

{

     //Display

     cout << this->GetFirstLine() << endl;

     //Call method

     IncrementPlayCount();

}

Playlist.h

//Include libraries

#ifndef PLAYLIST_H

#define PLAYLIST_H

#include <string>

#include <vector>

#include "Song.h"

//Use namespace

using namespace std;

//Define class

class Playlist

{

     //Define access specifier

     public:

     //Define constructor

     Playlist();

     //Define constructor

     Playlist(string playlistName);

     //Define method

     void lAddSngToPlylist(Song* songPtr);

     //Define method

     void lDeletSngFrmPlylst(Song* songPtr);

     //Define method

     string GetPlaylistName() const;

     //Define method

     vector<Song*> GetSongs() const;

     //Define access specifier

     private:

     //Declare variable

     string playlistName;

     //Create instance

     vector<Song*> songs;

};

//End

#endif

Playlist.cpp

//Include libraries

#include <string>

#include <vector>

#include "Song.h"

#include "Playlist.h"

//Use namespace

using namespace std;

//Define method

Playlist::Playlist()

{

     //Assign value

     this->playlistName = "none";

}

//Define method

Playlist::Playlist(string playlistName)

{

     //Assign value

     this->playlistName = playlistName;

}

//Define method

void Playlist::lAddSngToPlylist(Song* songPtr)

{

     //Assign value

     this->songs.push_back(songPtr);

}

//Define method

void Playlist::lDeletSngFrmPlylst(Song* songPtr)

{

     //Loop

     for (int li = 0; li < this->songs.size(); ++li)

     {

          //If condition satisfies

          if (this->songs.at(li) == songPtr)

          {

              //Assign value

              this->songs.erase(this->songs.begin() + li);

          }

     }

}

//Define method

string Playlist::GetPlaylistName() const

{

     //Return

     return this->playlistName;

}

//Define method

vector<Song*> Playlist::GetSongs() const

{

     //Return

     return this->songs;

}

Main.cpp

//Include libraries

#include <iostream>

#include <vector>

#include <cstdlib>

#include <limits>

#include "Song.h"

#include "Playlist.h"

//Use namespace

using namespace std;

//Declare variable

const int lQtPrgm = 0;

const int ADD_SONG = 1;

const int LIST_SONGS = 2;

const int ADD_PLAYLIST = 3;

const int ADD_SONG_TO_PLAYLIST = 4;

const int PLAY_PLAYLIST = 5;

const int SHUFFLE_SONGS = 6;

const int REMOVE_A_PLAYLIST = 7;

const int REMOVE_SONG_FROM_PLAYLIST = 8;

const int REMOVE_SONG_FROM_LIBRARY = 9;

const int LIST_OPTIONS = 10;

//Define method

void GetMenuChoice(int& menuChoice)

{

cout << "Enter your selection now (Enter 10 to list all options): ";

     cin >> menuChoice;

     cin.ignore(numeric_limits<std::streamsize>::max(), ' ');

     cout << endl;

     while (menuChoice == LIST_OPTIONS)

     {

cout << endl << "Please select one of the following options:" << endl << endl;

          cout << lQtPrgm << " - Quit the program" << endl;

          cout << ADD_SONG << " - Add songs" << endl;

          cout << LIST_SONGS << " - List all songs" << endl;

          cout << ADD_PLAYLIST << " - Add a playlist" << endl;

          cout << ADD_SONG_TO_PLAYLIST << " - Add a song to a playlist" << endl;

          cout << PLAY_PLAYLIST << " - Play a playlist" << endl;

          cout << SHUFFLE_SONGS << " - Play random songs" << endl;

          cout << REMOVE_A_PLAYLIST << " - Delete a whole playlist" << endl;

cout << REMOVE_SONG_FROM_PLAYLIST << " - Delete a song from a playlist" << endl;

cout << REMOVE_SONG_FROM_LIBRARY << " - Delete a song from everywhere" << endl;

cout << LIST_OPTIONS << " - List all options" << endl << endl;

cout << "Enter your selection now (Enter 10 to list all options): ";

          cin >> menuChoice;

               cin.ignore(numeric_limits<std::streamsize>::max(), ' ');

          cout << endl;

     }

}

//Define method

void lAdSng(vector<Song*>& songs)

{

     string lSngNme;

     string firstLine;

     int yearReleased;

     cout << "Read in Song names and first lines:" << endl;

     do

     {

          cout << "Song Name (type "STOP" when done): ";

          getline(cin, lSngNme);

          cout << endl << endl;

          if (lSngNme != "STOP")

          {

              cout << "That song's first line: ";

              getline(cin, firstLine);

              cout << endl << endl;

              cout << "The year that song was released: ";

              cin >> yearReleased;

                                 cin.ignore(numeric_limits<std::streamsize>::max(), ' ');

               cout << endl << endl;

              songs.push_back(new Song(lSngNme, firstLine, yearReleased));

          }

     }

     while (lSngNme != "STOP");

     cout << endl;

}

//Define method

void lAdPlylst(vector<Playlist*>& playlists)

{

     string lPlylstNme;

     cout << "Playlist name: ";

     getline(cin, lPlylstNme);

     cout << endl << endl;

     playlists.push_back(new Playlist(lPlylstNme));

}

//Define method

void lPrntAlSngsInf(const vector<Song*>& songs)

{

     for (int li = 0; li < songs.size(); ++li)

     {

          cout << li << ": ";

          songs.at(li)->PrintSongInfo();

     }

     cout << endl;

}

//Define method

void lPrntSngNmes(const vector<Song*>& songs)

{

     for (int li = 0; li < songs.size(); ++li)

     {

          cout << li << ": " << songs.at(li)->GetSongName() << endl;

     }

     cout << endl;

}

//Define method

void lPrntPlylst(const vector<Playlist*>& playlists, string promptMessage)

{

     cout << promptMessage << endl;

     for (int li = 0; li < playlists.size(); ++li)

     {

cout << li << ": " << playlists.at(li)->GetPlaylistName() << endl;

     }

     cout << "Pick a playlist index number: ";

}

//Define method

void lDlteSngPntrs(vector<Song*>& songs)

{

     const int lSTRTINDX = 0;

     while (songs.size() != 0)

     {

          delete songs.at(lSTRTINDX);

          songs.erase(songs.begin());

     }

}

//Define method

void lDltePlylstPntrs(vector<Playlist*>& playlists)

{

     const int lSTRTINDX = 0;

     while (playlists.size() != 0)

     {

          delete playlists.at(lSTRTINDX);

          playlists.erase(playlists.begin());

     }

}

//Define method

Playlist* lChsePlylst(const vector<Playlist*>& playlists, string promptMessage)

{

     int lChsnPlylst = 0;

     lPrntPlylst(playlists, promptMessage);

     cin >> lChsnPlylst;

     cin.ignore(numeric_limits<std::streamsize>::max(), ' ');

     cout << endl;

     return playlists.at(lChsnPlylst);

}

//Define method

Song* lChseSng(vector<Song*>& songs, string promptMessage)

{

     int lChsnSng = 0;

     cout << promptMessage << endl;

     lPrntSngNmes(songs);

     cout << "Pick a song index number: ";

     cin >> lChsnSng;

     cin.ignore(numeric_limits<std::streamsize>::max(), ' ');

     return songs.at(lChsnSng);

}

//Define method

void lAddSngToPlylist(vector<Playlist*>& playlists, vector<Song*>& songs)

{

     Playlist* lChsnPlylst = lChsePlylst(playlists, "Add to a playlist:");

     Song* lChsnSng = lChseSng(songs, "Find a song to add:");

     lChsnPlylst->lAddSngToPlylist(lChsnSng);

     cout << endl << endl;

}

//Define method

void lPlyPlylst(vector<Playlist*>& playlists)

{

     Playlist* lChsnPlylst = lChsePlylst(playlists, "Pick a playlist to play:");

     cout << "Playing first lines:" << endl;

     vector<Song*> lSngsInPlylst = lChsnPlylst->GetSongs();

     for (int li = 0; li < lSngsInPlylst.size(); ++li)

     {

          lSngsInPlylst.at(li)->PlaySong();

     }

}

//Define method

void ShuffleSongs(vector <Song*> songs)

{

     const int RAND_SEED = 42;

     int numSongsToShuffle = 0;

     int randomSongIndex = 0;

     srand(RAND_SEED);

     cout << "How many songs do you want played: ";

     cin >> numSongsToShuffle;

     cin.ignore(numeric_limits<std::streamsize>::max(), ' ');

     cout << endl;

     cout << "Playing random first lines:" << endl;

     for (int li = 0; li < numSongsToShuffle; ++li)

     {

          randomSongIndex = rand() % songs.size();

          songs.at(randomSongIndex)->PlaySong();

     }

}

//Define method

void lDeletSngFrmPlylst(vector <Playlist*>& playlists)

{

Playlist* lChsnPlylst = lChsePlylst(playlists, "Delete a song from a playlist:");

     vector<Song*> songs = lChsnPlylst->GetSongs();

     Song* lChsnSng = lChseSng(songs, "Choose the song to delete:");

     lChsnPlylst->lDeletSngFrmPlylst(lChsnSng);

}

//Define method

Song* lDeletSngFrmAlPlylst(vector <Playlist*>& playlists, vector<Song*>& songs)

{

     Playlist* lChsnPlylst = 0;

     Song* lChsnSng = lChseSng(songs, "Choose a song to delete:");

     for (int li = 0; li < playlists.size(); ++li)

     {

          lChsnPlylst = playlists.at(li);

          lChsnPlylst->lDeletSngFrmPlylst(lChsnSng);

     }

     return lChsnSng;

}

//Define method

void lDeletSngFrmLbry(vector <Playlist*>& playlists, vector<Song*>& songs)

{

     Song* lSngDelte = lDeletSngFrmAlPlylst(playlists, songs);

     for (int li = 0; li < songs.size(); ++li)

     {

          if (songs.at(li) == lSngDelte)

          {

              delete songs.at(li);

              songs.erase(songs.begin() + li);

          }

     }

}

//Define method

void lDltePlylst(vector <Playlist*>& playlists)

{

Playlist* lChsnPlylst = lChsePlylst(playlists, "Delete a whole playlist:");

     for (int li = 0; li < playlists.size(); ++li)

     {

          if (playlists.at(li) == lChsnPlylst)

          {

              delete playlists.at(li);

              playlists.erase(playlists.begin() + li);

          }

     }

}

//Define method

void lClnUpAlPntrs(vector<Playlist*>& playlists, vector<Song*>& songs)

{

     lDlteSngPntrs(songs);

     lDltePlylstPntrs(playlists);

}

//Define method

int main()

{

     int menuChoice = 0;

     vector<Song*> songs;

     vector<Playlist*> playlists;

     cout << "Welcome to the Firstline Player!" << endl << endl;

     do

     {

          GetMenuChoice(menuChoice);

          if (menuChoice == ADD_SONG)

          {

              lAdSng(songs);

          }

          else if (menuChoice == LIST_SONGS)

          {

              lPrntAlSngsInf(songs);

          }

          else if (menuChoice == ADD_PLAYLIST)

          {

              lAdPlylst(playlists);

          }

          else if (menuChoice == ADD_SONG_TO_PLAYLIST)

          {

              lAddSngToPlylist(playlists, songs);

          }

          else if (menuChoice == PLAY_PLAYLIST)

          {

              lPlyPlylst(playlists);

          }

          else if (menuChoice == SHUFFLE_SONGS)

          {

              ShuffleSongs(songs);

          }

          else if (menuChoice == REMOVE_A_PLAYLIST)

          {

              lDltePlylst(playlists);

          }

          else if (menuChoice == REMOVE_SONG_FROM_PLAYLIST)

          {

              lDeletSngFrmPlylst(playlists);

          }

          else if (menuChoice == REMOVE_SONG_FROM_LIBRARY)

          {

              lDeletSngFrmLbry(playlists, songs);

          }

     }

     while (menuChoice != lQtPrgm);

     lClnUpAlPntrs(playlists, songs);

     cout << "GOODBYE!";

     return 0;

}

Sample Output:

Welcome to the Firstline Player!

Enter your selection now (Enter 10 to list all options): 10

Please select one of the following options:

0 - Quit the program

1 - Add songs

2 - List all songs

3 - Add a playlist

4 - Add a song to a playlist

5 - Play a playlist

6 - Play random songs

7 - Delete a whole playlist

8 - Delete a song from a playlist

9 - Delete a song from everywhere

10 - List all options

Enter your selection now (Enter 10 to list all options): 1

Read in Song names and first lines:

Song Name (type "STOP" when done): Sdf

That song's first line: cjvjvvj

The year that song was released: 2017

Song Name (type "STOP" when done): STOP

Enter your selection now (Enter 10 to list all options): 10

Please select one of the following options:

0 - Quit the program

1 - Add songs

2 - List all songs

3 - Add a playlist

4 - Add a song to a playlist

5 - Play a playlist

6 - Play random songs

7 - Delete a whole playlist

8 - Delete a song from a playlist

9 - Delete a song from everywhere

10 - List all options

Enter your selection now (Enter 10 to list all options): 2

0: Name: "Sdf" FirstLine: "cjvjvvj" Released in: 2017 Played 0 times.

Enter your selection now (Enter 10 to list all options): 10

Please select one of the following options:

0 - Quit the program

1 - Add songs

2 - List all songs

3 - Add a playlist

4 - Add a song to a playlist

5 - Play a playlist

6 - Play random songs

7 - Delete a whole playlist

8 - Delete a song from a playlist

9 - Delete a song from everywhere

10 - List all options

Enter your selection now (Enter 10 to list all options):