Showing
17 changed files
with
3337 additions
and
0 deletions
Project.sln
0 → 100644
1 | + | ||
2 | +Microsoft Visual Studio Solution File, Format Version 12.00 | ||
3 | +# Visual Studio 15 | ||
4 | +VisualStudioVersion = 15.0.28010.2036 | ||
5 | +MinimumVisualStudioVersion = 10.0.40219.1 | ||
6 | +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Project", "Project\Project.vcxproj", "{488DFF6D-08D7-40A9-B10D-AE7374047D99}" | ||
7 | +EndProject | ||
8 | +Global | ||
9 | + GlobalSection(SolutionConfigurationPlatforms) = preSolution | ||
10 | + Debug|x64 = Debug|x64 | ||
11 | + Debug|x86 = Debug|x86 | ||
12 | + Release|x64 = Release|x64 | ||
13 | + Release|x86 = Release|x86 | ||
14 | + EndGlobalSection | ||
15 | + GlobalSection(ProjectConfigurationPlatforms) = postSolution | ||
16 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Debug|x64.ActiveCfg = Debug|x64 | ||
17 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Debug|x64.Build.0 = Debug|x64 | ||
18 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Debug|x86.ActiveCfg = Debug|Win32 | ||
19 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Debug|x86.Build.0 = Debug|Win32 | ||
20 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Release|x64.ActiveCfg = Release|x64 | ||
21 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Release|x64.Build.0 = Release|x64 | ||
22 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Release|x86.ActiveCfg = Release|Win32 | ||
23 | + {488DFF6D-08D7-40A9-B10D-AE7374047D99}.Release|x86.Build.0 = Release|Win32 | ||
24 | + EndGlobalSection | ||
25 | + GlobalSection(SolutionProperties) = preSolution | ||
26 | + HideSolutionNode = FALSE | ||
27 | + EndGlobalSection | ||
28 | + GlobalSection(ExtensibilityGlobals) = postSolution | ||
29 | + SolutionGuid = {13F536C0-2A1C-46D1-AC75-9315EF6D367F} | ||
30 | + EndGlobalSection | ||
31 | +EndGlobal |
Project/AlbumType.h
0 → 100644
1 | +#pragma once | ||
2 | +#include<string> | ||
3 | +using namespace std; | ||
4 | +#include"SimplifiedType.h" | ||
5 | +#include"SortedLinkedList.h" | ||
6 | + | ||
7 | +class AlbumType { | ||
8 | +public: | ||
9 | + | ||
10 | + AlbumType() | ||
11 | + { | ||
12 | + AlbumName = ""; | ||
13 | + ArtistName = ""; | ||
14 | + } //기본 생성자 | ||
15 | + ~AlbumType() | ||
16 | + { | ||
17 | + | ||
18 | + } //기본 소멸자 | ||
19 | + /** | ||
20 | +* @brief AlbumType의 생성자이다. | ||
21 | +* @pre x | ||
22 | +* @post AlbumType이 생성된다. | ||
23 | + @param albumname 앨범명 | ||
24 | + @param artistname 이 앨범을 낸 아티스트명 | ||
25 | +*/ | ||
26 | + AlbumType(string albumname, string artistname) | ||
27 | + { | ||
28 | + AlbumName = albumname; | ||
29 | + ArtistName = artistname; | ||
30 | + } | ||
31 | + AlbumType(const AlbumType& data) | ||
32 | + { | ||
33 | + AlbumName = data.AlbumName; | ||
34 | + ArtistName = data.ArtistName; | ||
35 | + } | ||
36 | + /** | ||
37 | +* @brief AlbumName 을 set한다. | ||
38 | +* @pre x | ||
39 | +* @post AlbumName is set | ||
40 | +* @return x | ||
41 | +*/ | ||
42 | + void SetAlbumName(string Name) | ||
43 | + { | ||
44 | + AlbumName = Name; | ||
45 | + }; | ||
46 | + /** | ||
47 | +* @brief ArtistName을 set한다. | ||
48 | +* @pre x | ||
49 | +* @post ArtistName is set | ||
50 | +* @return x | ||
51 | +*/ | ||
52 | + void SetArtistName(string Name) | ||
53 | + { | ||
54 | + ArtistName = Name; | ||
55 | + }; | ||
56 | + /** | ||
57 | +* @brief get AlbumName | ||
58 | +* @pre AlbumName is set | ||
59 | +* @post x | ||
60 | +* @return AlbumName | ||
61 | +*/ | ||
62 | + string GetAlbumName() | ||
63 | + { | ||
64 | + return AlbumName; | ||
65 | + }; | ||
66 | + /** | ||
67 | +* @brief getArtistName | ||
68 | +* @pre ArtistName is set | ||
69 | +* @post x | ||
70 | +* @return ArtistName | ||
71 | +*/ | ||
72 | + string GetArtistName() | ||
73 | + { | ||
74 | + return ArtistName; | ||
75 | + }; | ||
76 | + /** | ||
77 | +* @brief 비교 연산자 | ||
78 | +* @pre 비교하려는 두 앨범타입이 초기화되어 있어야한다 | ||
79 | +* @post x | ||
80 | +* @param data 비교하려는 앨범타입 | ||
81 | +* @return 좌변이크면 false, 우변이크면 true | ||
82 | +*/ | ||
83 | + bool operator<(AlbumType data) | ||
84 | + { | ||
85 | + if (AlbumName == data.GetAlbumName()) | ||
86 | + return (ArtistName < data.GetArtistName()); | ||
87 | + else | ||
88 | + return (AlbumName < data.GetAlbumName()); | ||
89 | + }; | ||
90 | + /** | ||
91 | +* @brief 비교 연산자 | ||
92 | +* @pre 비교하려는 두 앨범타입이 초기화되어 있어야한다 | ||
93 | +* @post x | ||
94 | +* @param data 비교하려는 앨범타입 | ||
95 | +* @return 좌변이크면 true, 우변이크면 false | ||
96 | +*/ | ||
97 | + bool operator>(AlbumType data) | ||
98 | + { | ||
99 | + if (AlbumName == data.GetAlbumName()) | ||
100 | + return (ArtistName > data.GetArtistName()); | ||
101 | + else | ||
102 | + return (AlbumName > data.GetAlbumName()); | ||
103 | + }; | ||
104 | + /** | ||
105 | +* @brief 등위연산자 | ||
106 | +* @pre 비교하려는 두 앨범타입이 초기화되어 있어야한다 | ||
107 | +* @post x | ||
108 | +* @param data 비교하려는 앨범타입 | ||
109 | +* @return 두 항이 같으면 true 아니면 false | ||
110 | +*/ | ||
111 | + bool operator==(AlbumType data) { | ||
112 | + if (AlbumName == data.GetAlbumName() && ArtistName == data.GetArtistName()) | ||
113 | + return true; | ||
114 | + else | ||
115 | + return false; | ||
116 | + }; | ||
117 | +private: | ||
118 | + string AlbumName; //앨범 이름을 저장할 변수 | ||
119 | + string ArtistName; //앨범의 아티스트를 저장할 변수 | ||
120 | + | ||
121 | +}; |
Project/Application.cpp
0 → 100644
1 | +#include"Application.h" | ||
2 | + | ||
3 | + | ||
4 | + | ||
5 | +// Program driver. | ||
6 | +void Application::Run() | ||
7 | +{ | ||
8 | + while (1) | ||
9 | + { | ||
10 | + m_Command = GetCommand(); | ||
11 | + | ||
12 | + switch (m_Command) | ||
13 | + { | ||
14 | + case 1: // read a record and add to list. | ||
15 | + AddMusic(); | ||
16 | + break; | ||
17 | + case 2: // display all the records in list on screen. | ||
18 | + Delete(); | ||
19 | + break; | ||
20 | + case 3: | ||
21 | + Update(); | ||
22 | + break; | ||
23 | + case 4: //곡명으로 검색 | ||
24 | + RetreiveRecordByName(); | ||
25 | + break; | ||
26 | + case 5: //가수명으로 검색 | ||
27 | + RetreiveRecordBySinger(); | ||
28 | + break; | ||
29 | + case 6: //앨범명으로 검색 | ||
30 | + RetreiveRecordByAlbum(); | ||
31 | + break; | ||
32 | + case 7: //장르로 검색 | ||
33 | + RetreiveRecordByGenre(); | ||
34 | + break; | ||
35 | + case 8: // load list data from a file. | ||
36 | + DisplayAllMusic(); | ||
37 | + break; | ||
38 | + case 9: | ||
39 | + DIsplayNewMusic(); | ||
40 | + break; | ||
41 | + case 10: | ||
42 | + DisplayMusicbyGenre(); | ||
43 | + break; | ||
44 | + case 11: | ||
45 | + RetreiveRecordByNameNGenre(); | ||
46 | + break; | ||
47 | + case 12: | ||
48 | + DisplayMusicByAlbum(); | ||
49 | + break; | ||
50 | + case 13: | ||
51 | + DisplayMusicByArtist(); | ||
52 | + break; | ||
53 | + case 20: | ||
54 | + makePlayList(); | ||
55 | + break; | ||
56 | + case 21: | ||
57 | + AddMusicInPL(); | ||
58 | + break; | ||
59 | + case 22: | ||
60 | + PrintPL(); | ||
61 | + break; | ||
62 | + case 98: | ||
63 | + ReadDataFromFile(); | ||
64 | + break; | ||
65 | + case 99: | ||
66 | + WriteDataToFile(); | ||
67 | + case 0: | ||
68 | + return; | ||
69 | + default: | ||
70 | + cout << "\tIllegal selection...\n"; | ||
71 | + break; | ||
72 | + } | ||
73 | + } | ||
74 | +} | ||
75 | + | ||
76 | + | ||
77 | +// Display command on screen and get a input from keyboard. | ||
78 | +int Application::GetCommand() | ||
79 | +{ | ||
80 | + int command; | ||
81 | + cout << endl << endl; | ||
82 | + cout << "\t---ID -- Command ----- " << endl; | ||
83 | + cout << "\t 1 : Add Music" << endl; | ||
84 | + cout << "\t 2 : Delete Music" << endl; | ||
85 | + cout << "\t 3 : Replace Music" << endl; | ||
86 | + cout << "\t 4 : Search by Song Name" << endl; | ||
87 | + cout << "\t 5 : Search by Artist(Singer)" << endl; | ||
88 | + cout << "\t 6 : Search by Album" << endl; | ||
89 | + cout << "\t 7 : Search by Genre" << endl; | ||
90 | + cout << "\t 8 : Display all Music" << endl; | ||
91 | + cout << "\t 9 : Display New Music" << endl; | ||
92 | + cout << "\t 10 : Display Music by Genre" << endl; | ||
93 | + cout << "\t 11 : search by Name and Genre" << endl; | ||
94 | + cout << "\t 12 : Display Music by Album" << endl; | ||
95 | + cout << "\t 13 : Display Music by Artist" << endl; | ||
96 | + cout << "\t 20 : 재생목록 만들기" << endl; | ||
97 | + cout << "\t 21 : 재생목록에 추가하기" << endl; | ||
98 | + cout << "\t 22 : 재생목록 보기" << endl; | ||
99 | + cout << "\t 30 : 재생하기" << endl; | ||
100 | + cout << "\t 98 : Get from file" << endl; | ||
101 | + cout << "\t 99 : Put to file " << endl; | ||
102 | + cout << "\t 0 : Quit" << endl; | ||
103 | + | ||
104 | + cout << endl << "\t Choose a Command--> "; | ||
105 | + cin >> command; | ||
106 | + cout << endl; | ||
107 | + | ||
108 | + return command; | ||
109 | +} | ||
110 | + | ||
111 | + | ||
112 | +// Add new record into list. | ||
113 | +int Application::AddMusic() | ||
114 | +{ | ||
115 | + string genre; //장르를 저장할 임시변수 | ||
116 | + string name; //곡명을 저장할 임시변수 | ||
117 | + MusicType item; | ||
118 | + SimplifiedType Simpletype; //곡번호, 곡명만 저장할 타입 | ||
119 | + item.SetInfoFromKB(); | ||
120 | + m_List.Add(item); //MusicList에 원소 추가 | ||
121 | + RemakeSubList(); //MusicList에 변화가 생겼으므로 하위 리스트들을 다시 만들어줘야 한다. | ||
122 | + SetMusicIndex(); //MusicList에 변화가 생겼으므로 Index를 다시 부여한다. | ||
123 | + DoublyIter<MusicType> Miter(m_List); | ||
124 | + ManageType mgitem; | ||
125 | + while (Miter.NotNull()) | ||
126 | + { | ||
127 | + if (Miter.GetCurrentNode().data == item) | ||
128 | + { | ||
129 | + mgitem.setIndex(Miter.GetCurrentNode().data.GetNum()); | ||
130 | + } | ||
131 | + Miter.Next(); | ||
132 | + } | ||
133 | + mgitem.setName(item.GetName()); | ||
134 | + mgitem.setPkey(item.GetPkey()); | ||
135 | + mgitem.setArtist(item.GetSinger()); | ||
136 | + mg_List.Add(mgitem); | ||
137 | + | ||
138 | + //최근 추가목록에 추가하기 | ||
139 | + /* | ||
140 | + | ||
141 | + | ||
142 | + | ||
143 | + Simpletype.SetRecord(num, name); | ||
144 | + if (!AddRecentlyMusicList.IsFull()) //최근 추가된목록이 가득차지 않았을경우 | ||
145 | + AddRecentlyMusicList.EnQueue(Simpletype); //큐에 하나 추가 | ||
146 | + else //최근 추가된목록이 30개 꽉 찼을경우 | ||
147 | + { | ||
148 | + SimplifiedType S_temp; | ||
149 | + AddRecentlyMusicList.DeQueue(S_temp); //하나를 지우고 | ||
150 | + AddRecentlyMusicList.EnQueue(Simpletype); //방금 추가된 레코드를 집어넣는다 | ||
151 | + } | ||
152 | + */ | ||
153 | + // 현재 list 출력 | ||
154 | + DisplayAllMusic(); | ||
155 | + | ||
156 | + return 1; | ||
157 | +} | ||
158 | + | ||
159 | + | ||
160 | +// Display all records in the list on screen. | ||
161 | +void Application::DisplayAllMusic() | ||
162 | +{ | ||
163 | + DoublyIter<MusicType> iter(m_List); | ||
164 | + cout << "\n\tCurrent list" << endl; | ||
165 | + | ||
166 | + // list의 모든 데이터를 화면에 출력 | ||
167 | + while (iter.NotNull()) | ||
168 | + { | ||
169 | + iter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
170 | + iter.Next(); | ||
171 | + | ||
172 | + } | ||
173 | + | ||
174 | +} | ||
175 | + | ||
176 | + | ||
177 | + | ||
178 | +//찾을 ID를 사용자에게 입력받고 SortedList의 Delete함수를 호출한다. | ||
179 | +void Application::Delete() | ||
180 | +{ | ||
181 | + cout << "\t지울 : "; | ||
182 | + MusicType data; //Delete함수는 MusicType을 파라미터로 갖기 때문에 임의로 만들어준다. | ||
183 | + data.SetNumFromKB(); //사용자에게서 곡 번호를 입력받는다. | ||
184 | + SearchByIndex(data); | ||
185 | + | ||
186 | + if (m_List.Delete(data)) //Delete함수에 data를 넘겨준다. | ||
187 | + { | ||
188 | + cout << "\t삭제를 완료했습니다." << endl; //삭제에 성공했으면 메시지를 출력한다. | ||
189 | + RemakeSubList(); //MusicList에 변화가 생겼으므로 하위 리스트들을 다시 만들어줘야 한다. | ||
190 | + if (m_List.GetLength() != 0) //길이가 0이면 인덱스를 부여할수 없다. | ||
191 | + { | ||
192 | + SetMusicIndex();//MusicList에 변화가 생겼으므로 Index를 다시 부여한다. | ||
193 | + } | ||
194 | + } | ||
195 | + else | ||
196 | + cout << "\t삭제하지 못했습니다. 일치하는 항목을 찾을 수 없습니다." << endl; //삭제에 실패했으면 메시지를 출력한다. | ||
197 | + | ||
198 | + | ||
199 | +} | ||
200 | + | ||
201 | + | ||
202 | +//찾을 ID를 사용자에게 입력받고 SortedList의 Update함수를 호출한다. | ||
203 | +void Application::Update() | ||
204 | +{ | ||
205 | + cout << "\t변경을 원하는 항목의 "; | ||
206 | + MusicType data; //Replace함수는 MusicType을 파라미터로 갖기 때문에 임의로 만들어준다. | ||
207 | + data.SetNumFromKB(); //사용자에게서 수정할 항목의 곡 번호를 입력받는다. | ||
208 | + SearchByIndex(data); | ||
209 | + if (!m_List.Get(data)) //사용자가 입력한 항목이 List에 있나 검색 | ||
210 | + { | ||
211 | + cout << "\t항목을 찾을 수 없습니다." << endl; //찾을 수 없을때 메시지를 출력한다. | ||
212 | + return; | ||
213 | + } | ||
214 | + else //찾을 수 있을때 | ||
215 | + { | ||
216 | + data.SetNameFromKB(); //사용자에게서 곡명을 입력받는다. | ||
217 | + data.SetSingerFromKB(); //사용자에게서 가수를 입력받는다. | ||
218 | + data.SetAlbumFromKB(); //사용자에게서 앨범을 입력받는다. | ||
219 | + data.SetGenreFromKB(); //사용자에게서 장르를 입력받는다. | ||
220 | + data.SetLyricsFromKB(); // 사용자에게서 가사를 입력받는다. | ||
221 | + if (m_List.Delete(data))//기존 항목을 삭제하고 | ||
222 | + { | ||
223 | + data.SetPkey(); //데이터를 변경했으므로 Pkey를 다시 지정해준다. | ||
224 | + m_List.Add(data); | ||
225 | + cout << "\t수정을 완료했습니다." << endl; //수정을 성공했을 때 메시지를 출력한다. | ||
226 | + RemakeSubList(); //MusicList에 변화가 생겼으므로 하위 리스트들을 다시 만들어줘야 한다. | ||
227 | + if (m_List.GetLength() != 0) //길이가 0이면 인덱스를 부여할수 없다. | ||
228 | + { | ||
229 | + SetMusicIndex();//MusicList에 변화가 생겼으므로 Index를 다시 부여한다. | ||
230 | + } | ||
231 | + } | ||
232 | + else | ||
233 | + cout << "\t수정을 실패했습니다." << endl; //수정에 실패했을 때 메시지를 출력한다. | ||
234 | + } | ||
235 | + | ||
236 | +} | ||
237 | +//사용자에게 찾고자하는 Name을 입력받고 넘겨주는 역할을 한다. | ||
238 | +void Application::RetreiveRecordByName() | ||
239 | +{ | ||
240 | + MusicType temp; | ||
241 | + cout << "\t찾을 "; | ||
242 | + temp.SetNameFromKB(); //SearchByName함수에 넘겨줄 temp의 Name을 사용자에게 입력받는다. | ||
243 | + SearchByName(temp); //실질적으로 찾는 동작을 하는 SearchByName함수를 호출하고 temp값을 넘겨준다. | ||
244 | +} | ||
245 | + | ||
246 | + | ||
247 | +//사용자가 찾고자하는 Name을 포함하는 inData로 m_List의 항목들 중 일치하는 항목을 찾고 출력해준다. **프로그램에 전반적으로 Array에 index를 직접 접근하는 방법을 선호했으나 이 함수는 Application 클래스의 메소드이므로 GetNextItem함수를 이용해 iteration을 이용했습니다. | ||
248 | +void Application::SearchByName(MusicType &inData) | ||
249 | +{ | ||
250 | + MusicType temp; //m_List의 값을 비교해주기 위한 임시 MusicType. | ||
251 | + DoublyIter<MusicType> iter(m_List); | ||
252 | + int count = 0; | ||
253 | + while (iter.NotNull()) | ||
254 | + { | ||
255 | + if (iter.GetCurrentNode().data.GetName().find(inData.GetName()) != -1) | ||
256 | + { | ||
257 | + iter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
258 | + count++; | ||
259 | + } | ||
260 | + iter.Next(); | ||
261 | + } | ||
262 | + | ||
263 | + | ||
264 | + | ||
265 | + | ||
266 | + if (count == 0) | ||
267 | + cout << "\t찾을 수 없습니다." << endl; //찾은 개수가 0개이면 찾을 수 없다는 메시지를 출력한다. | ||
268 | +} | ||
269 | + | ||
270 | +//사용자에게 찾고자하는 Singer을 입력받고 넘겨주는 역할을 한다. | ||
271 | +void Application::RetreiveRecordBySinger() | ||
272 | +{ | ||
273 | + MusicType temp; | ||
274 | + cout << "\t찾을 "; | ||
275 | + temp.SetSingerFromKB(); //SearchBySinger함수에 넘겨줄 temp의 Name을 사용자에게 입력받는다. | ||
276 | + SearchBySinger(temp); //실질적으로 찾는 동작을 하는 SearchBySinger함수를 호출하고 temp값을 넘겨준다. | ||
277 | +} | ||
278 | + | ||
279 | + | ||
280 | +//사용자가 찾고자하는 Singer을 포함하는 inData로 m_List의 항목들 중 일치하는 항목을 찾고 출력해준다. **프로그램에 전반적으로 Array에 index를 직접 접근하는 방법을 선호했으나 이 함수는 Application 클래스의 메소드이므로 GetNextItem함수를 이용해 iteration을 이용했습니다. | ||
281 | +void Application::SearchBySinger(MusicType &inData) | ||
282 | +{ | ||
283 | + MusicType temp; //m_List의 값을 비교해주기 위한 임시 MusicType. | ||
284 | + DoublyIter<MusicType> iter(m_List); | ||
285 | + int count = 0; | ||
286 | + while (iter.NotNull()) | ||
287 | + { | ||
288 | + if (iter.GetCurrentNode().data.GetSinger().find(inData.GetSinger()) != -1) | ||
289 | + { | ||
290 | + iter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
291 | + count++; | ||
292 | + } | ||
293 | + iter.Next(); | ||
294 | + } | ||
295 | + if (count == 0) | ||
296 | + cout << "\t찾을 수 없습니다." << endl; //찾은 개수가 0개이면 찾을 수 없다는 메시지를 출력한다. | ||
297 | +} | ||
298 | + | ||
299 | +//사용자에게 찾고자하는 Album을 입력받고 넘겨주는 역할을 한다. | ||
300 | +void Application::RetreiveRecordByAlbum() | ||
301 | +{ | ||
302 | + MusicType temp; | ||
303 | + cout << "\t찾을 "; | ||
304 | + temp.SetAlbumFromKB(); //SearchByAlbum함수에 넘겨줄 temp의 Album을 사용자에게 입력받는다. | ||
305 | + SearchByAlbum(temp); //실질적으로 찾는 동작을 하는 SearchByAlbum함수를 호출하고 temp값을 넘겨준다. | ||
306 | +} | ||
307 | + | ||
308 | + | ||
309 | +//사용자가 찾고자하는 Album을 포함하는 inData로 m_List의 항목들 중 일치하는 항목을 찾고 출력해준다. **프로그램에 전반적으로 Array에 index를 직접 접근하는 방법을 선호했으나 이 함수는 Application 클래스의 메소드이므로 GetNextItem함수를 이용해 iteration을 이용했습니다. | ||
310 | +void Application::SearchByAlbum(MusicType &inData) | ||
311 | +{ | ||
312 | + if (m_List.IsEmpty() == true) | ||
313 | + { | ||
314 | + cout << "리스트에 아무것도 없습니다." << endl; | ||
315 | + return; | ||
316 | + } | ||
317 | + MusicType temp; //m_List의 값을 비교해주기 위한 임시 MusicType. | ||
318 | + DoublyIter<MusicType> iter(m_List); | ||
319 | + int count = 0; | ||
320 | + while (iter.NotNull()) | ||
321 | + { | ||
322 | + if (iter.GetCurrentNode().data.GetAlbum().find(inData.GetAlbum()) != -1) | ||
323 | + { | ||
324 | + iter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
325 | + count++; | ||
326 | + } | ||
327 | + iter.Next(); | ||
328 | + } | ||
329 | + if (count == 0) | ||
330 | + cout << "\t찾을 수 없습니다." << endl; //찾은 개수가 0개이면 찾을 수 없다는 메시지를 출력한다. | ||
331 | +} | ||
332 | +//사용자에게 찾고자하는 Genre을 입력받고 넘겨주는 역할을 한다. | ||
333 | +void Application::RetreiveRecordByGenre() | ||
334 | +{ | ||
335 | + MusicType temp; | ||
336 | + cout << "\t찾을 "; | ||
337 | + temp.SetGenreFromKB(); //SearchByGenre함수에 넘겨줄 temp의 Genre을 사용자에게 입력받는다. | ||
338 | + SearchByGenre(temp); //실질적으로 찾는 동작을 하는 SearchByGenre함수를 호출하고 temp값을 넘겨준다. | ||
339 | +} | ||
340 | + | ||
341 | + | ||
342 | +//사용자가 찾고자하는 Genre을 포함하는 inData로 m_List의 항목들 중 일치하는 항목을 찾고 출력해준다. **프로그램에 전반적으로 Array에 index를 직접 접근하는 방법을 선호했으나 이 함수는 Application 클래스의 메소드이므로 GetNextItem함수를 이용해 iteration을 이용했습니다. | ||
343 | +void Application::SearchByGenre(MusicType &inData) | ||
344 | +{ | ||
345 | + if (m_List.IsEmpty() == true) | ||
346 | + { | ||
347 | + cout << "리스트에 아무것도 없습니다." << endl; | ||
348 | + return; | ||
349 | + } | ||
350 | + MusicType temp; //m_List의 값을 비교해주기 위한 임시 MusicType. | ||
351 | + DoublyIter<MusicType> iter(m_List); | ||
352 | + int count = 0; | ||
353 | + while (iter.NotNull()) | ||
354 | + { | ||
355 | + if (iter.GetCurrentNode().data.GetGenre().find(inData.GetGenre()) != -1) | ||
356 | + { | ||
357 | + iter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
358 | + count++; | ||
359 | + } | ||
360 | + iter.Next(); | ||
361 | + } | ||
362 | + if (count == 0) | ||
363 | + cout << "\t찾을 수 없습니다." << endl; //찾은 개수가 0개이면 찾을 수 없다는 메시지를 출력한다. | ||
364 | +} | ||
365 | + | ||
366 | +// Open a file by file descriptor as an input file. | ||
367 | +int Application::OpenInFile(char *fileName) | ||
368 | +{ | ||
369 | + m_InFile.open(fileName); // file open for reading. | ||
370 | + | ||
371 | + // 파일 오픈에 성공하면 1, 그렇지 않다면 0을 리턴. | ||
372 | + if (!m_InFile) return 0; | ||
373 | + else return 1; | ||
374 | +} | ||
375 | + | ||
376 | + | ||
377 | +// Open a file by file descriptor as an output file. | ||
378 | +int Application::OpenOutFile(char *fileName) | ||
379 | +{ | ||
380 | + m_OutFile.open(fileName); // file open for writing. | ||
381 | + | ||
382 | + // 파일 오픈에 성공하면 1, 그렇지 않다면 0을 리턴. | ||
383 | + if (!m_OutFile) return 0; | ||
384 | + else return 1; | ||
385 | +} | ||
386 | + | ||
387 | + | ||
388 | +// Open a file as a read mode, read all data on the file, and set list by the data. | ||
389 | +int Application::ReadDataFromFile() | ||
390 | +{ | ||
391 | + | ||
392 | + MusicType data; // 읽기용 임시 변수 | ||
393 | + ifstream ReadData; | ||
394 | + ReadData.open("text.txt"); | ||
395 | + string OneLine; | ||
396 | + while (getline(ReadData, OneLine)) | ||
397 | + { | ||
398 | + istringstream L(OneLine); | ||
399 | + string name, singer, Album, Genre, Lyrics; | ||
400 | + L >> name; | ||
401 | + L >> singer; | ||
402 | + L >> Album; | ||
403 | + L >> Genre; | ||
404 | + L >> Lyrics; | ||
405 | + data.SetRecord(name, singer, Album, Genre, Lyrics); | ||
406 | + m_List.Add(data); | ||
407 | + } | ||
408 | + /* | ||
409 | + char fileName[FILENameSIZE]; | ||
410 | + cout << "\n\tEnter Input file Name : "; | ||
411 | + cin >> fileName; | ||
412 | + | ||
413 | + // file open, open error가 발생하면 0을 리턴 | ||
414 | + if (!OpenInFile(fileName)) | ||
415 | + return 0; | ||
416 | + | ||
417 | + // 파일의 모든 내용을 읽어 list에 추가 | ||
418 | + while (!m_InFile.eof()) | ||
419 | + { | ||
420 | + // array에 학생들의 정보가 들어있는 structure 저장 | ||
421 | + data.ReadDataFromFile(m_InFile); | ||
422 | + m_List.Add(data); | ||
423 | + } | ||
424 | + | ||
425 | + m_InFile.close(); // file close | ||
426 | + */ | ||
427 | + SetMusicIndex(); | ||
428 | + // 현재 list 출력 | ||
429 | + DisplayAllMusic(); | ||
430 | + | ||
431 | + return 1; | ||
432 | +} | ||
433 | + | ||
434 | + | ||
435 | +// Open a file as a write mode, and write all data into the file, | ||
436 | +int Application::WriteDataToFile() | ||
437 | +{ | ||
438 | + | ||
439 | + m_OutFile.close(); // file close | ||
440 | + | ||
441 | + return 1; | ||
442 | +} | ||
443 | + | ||
444 | +//최근 추가된 30곡 출력 | ||
445 | +void Application::DIsplayNewMusic() | ||
446 | +{ | ||
447 | + | ||
448 | + if (m_List.IsEmpty() == true) | ||
449 | + { | ||
450 | + cout << "리스트에 아무것도 없습니다." << endl; | ||
451 | + return; | ||
452 | + } | ||
453 | + int cnt = 0; | ||
454 | + DoublyIter2<ManageType> Mgiter(mg_List); | ||
455 | + Mgiter.Last(); | ||
456 | + while (Mgiter.NotNull() && cnt < 30) | ||
457 | + { | ||
458 | + Mgiter.GetCurrentNode().data.PrintNameNIndex(); | ||
459 | + Mgiter.Prev(); | ||
460 | + cnt++; | ||
461 | + } | ||
462 | + | ||
463 | + | ||
464 | + | ||
465 | + | ||
466 | + | ||
467 | +} | ||
468 | + | ||
469 | +bool Application::Search(int key, MusicType& inData) | ||
470 | +{ | ||
471 | + inData.SetNum(key); | ||
472 | + if (m_List.Get(inData)) | ||
473 | + return true; | ||
474 | + | ||
475 | + else | ||
476 | + return false; | ||
477 | +} | ||
478 | +//Display Music by genre through genre list | ||
479 | +void Application::DisplayMusicbyGenre() | ||
480 | +{ | ||
481 | + if (m_List.GetLength() == 0) | ||
482 | + return; | ||
483 | + if (RemakeGenreList == true) | ||
484 | + { | ||
485 | + GenreList.MakeEmpty(); //기존의 리스트를 비운다 | ||
486 | + DoublyIter<MusicType> Miter(m_List); | ||
487 | + while (Miter.NotNull()) | ||
488 | + { | ||
489 | + string thisGenre; | ||
490 | + thisGenre = Miter.GetCurrentNode().data.GetGenre(); | ||
491 | + GenreList.Add(thisGenre); | ||
492 | + Miter.Next(); | ||
493 | + } //이 반복문이 끝나면 장르리스트에 장르가 정렬되어 들어감 | ||
494 | + } | ||
495 | + RemakeGenreList = false; //리스트를 다시 만들었으므로 변경이 없으면 다시 만들필요가 없다 | ||
496 | + | ||
497 | + //아래는 출력하는 코드 | ||
498 | + DoublyIter<string> Giter(GenreList); | ||
499 | + string thisGenre; | ||
500 | + while (Giter.NotNull()) | ||
501 | + { | ||
502 | + thisGenre = Giter.GetCurrentNode().data; | ||
503 | + DoublyIter<MusicType> Miter2(m_List); | ||
504 | + cout << "\t장르 : " << Miter2.GetCurrentNode().data.GetGenre() << endl; | ||
505 | + while (Miter2.NotNull()) | ||
506 | + { | ||
507 | + | ||
508 | + if (thisGenre == Miter2.GetCurrentNode().data.GetGenre()) | ||
509 | + { | ||
510 | + cout << "트랙넘버 : " << Miter2.GetCurrentNode().data.GetName() << endl; | ||
511 | + cout << "곡명 : " << Miter2.GetCurrentNode().data.GetName() << endl; | ||
512 | + } | ||
513 | + Miter2.Next(); | ||
514 | + } | ||
515 | + cout << "\t -------------------------" << endl; | ||
516 | + Giter.Next(); | ||
517 | + } | ||
518 | + | ||
519 | + | ||
520 | + | ||
521 | +} | ||
522 | + | ||
523 | + | ||
524 | + | ||
525 | +//name 과 genre 정보를 받아 Search함수에 넘긴다. | ||
526 | +void Application::RetreiveRecordByNameNGenre() | ||
527 | +{ | ||
528 | + MusicType temp; | ||
529 | + cout << "\t찾을 "; | ||
530 | + temp.SetNameFromKB(); | ||
531 | + temp.SetGenreFromKB(); //SearchByGenre함수에 넘겨줄 temp의 Genre을 사용자에게 입력받는다. | ||
532 | + SearchByNameNGenre(temp); //실질적으로 찾는 동작을 하는 SearchByGenre함수를 호출하고 temp값을 넘겨준다. | ||
533 | + | ||
534 | + | ||
535 | +} | ||
536 | + | ||
537 | +void Application::SearchByNameNGenre(MusicType& inData) | ||
538 | +{ | ||
539 | + if (m_List.IsEmpty() == true) | ||
540 | + { | ||
541 | + cout << "리스트에 아무것도 없습니다." << endl; | ||
542 | + return; | ||
543 | + } | ||
544 | + MusicType temp; //m_List의 값을 비교해주기 위한 임시 MusicType. | ||
545 | + DoublyIter<MusicType> iter(m_List); | ||
546 | + int count = 0; | ||
547 | + while (iter.NotNull()) | ||
548 | + { | ||
549 | + if (iter.GetCurrentNode().data.GetName().find(inData.GetName()) != -1 && iter.GetCurrentNode().data.GetGenre().find(inData.GetGenre()) != -1) | ||
550 | + { | ||
551 | + iter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
552 | + count++; | ||
553 | + } | ||
554 | + iter.Next(); | ||
555 | + } | ||
556 | + if (count == 0) | ||
557 | + cout << "\t찾을 수 없습니다." << endl; //찾은 개수가 0개이면 찾을 수 없다는 메시지를 출력한다. | ||
558 | + | ||
559 | + | ||
560 | +} | ||
561 | + | ||
562 | +void Application::DisplayMusicByAlbum() | ||
563 | +{ | ||
564 | + | ||
565 | + if (m_List.GetLength() == 0) | ||
566 | + return; | ||
567 | + //쉽게 구현하기 | ||
568 | + if (RemakeAlbumList == true) //앨범 리스트를 다시만들어야 하는가 | ||
569 | + { | ||
570 | + AlbumList.MakeEmpty(); | ||
571 | + DoublyIter<MusicType> Miter(m_List); | ||
572 | + while (Miter.NotNull()) | ||
573 | + { | ||
574 | + AlbumType thisAlbum(Miter.GetCurrentNode().data.GetAlbum(), Miter.GetCurrentNode().data.GetSinger()); | ||
575 | + AlbumList.Add(thisAlbum); | ||
576 | + Miter.Next(); | ||
577 | + } | ||
578 | + } | ||
579 | + RemakeAlbumList = false; //리스트를 갱신했으므로 다시만들 필요가 없다. | ||
580 | + //여기서부터는 출력코드 | ||
581 | + | ||
582 | + | ||
583 | + DoublyIter<AlbumType> Abiter(AlbumList); | ||
584 | + while (Abiter.NotNull()) | ||
585 | + { | ||
586 | + DoublyIter<MusicType> Miter2(m_List); | ||
587 | + cout << "\t앨범명 : " << Abiter.GetCurrentNode().data.GetAlbumName() << endl; | ||
588 | + cout << "\t아티스트명 : " << Abiter.GetCurrentNode().data.GetArtistName() << endl; | ||
589 | + while (Miter2.NotNull()) | ||
590 | + { | ||
591 | + | ||
592 | + if (Miter2.GetCurrentNode().data.GetAlbum() == Abiter.GetCurrentNode().data.GetAlbumName() && Miter2.GetCurrentNode().data.GetSinger() == Abiter.GetCurrentNode().data.GetArtistName()) | ||
593 | + { | ||
594 | + cout << "\t트랙넘버 : " << Miter2.GetCurrentNode().data.GetName() << endl; | ||
595 | + cout << "\t곡명 : " << Miter2.GetCurrentNode().data.GetName() << endl; | ||
596 | + | ||
597 | + } | ||
598 | + Miter2.Next(); | ||
599 | + } | ||
600 | + cout << "\t-------------------------" << endl; | ||
601 | + Abiter.Next(); | ||
602 | + } | ||
603 | + | ||
604 | + | ||
605 | + | ||
606 | + | ||
607 | + | ||
608 | + | ||
609 | +} | ||
610 | + | ||
611 | +void Application::DisplayMusicByArtist() | ||
612 | +{ | ||
613 | + if (m_List.GetLength() == 0) | ||
614 | + return; | ||
615 | + if (RemakeArtistList == true) //아티스트 리스트를 다시 만들어야 하는가 | ||
616 | + { | ||
617 | + ArtistList.MakeEmpty(); | ||
618 | + AlbumList.MakeEmpty(); //아티스트 리스트와 앨범리스트를 비운다 | ||
619 | + DoublyIter<MusicType> Miter(m_List); | ||
620 | + while (Miter.NotNull()) | ||
621 | + { | ||
622 | + ArtistType thisArtist; | ||
623 | + thisArtist.SetArtistName(Miter.GetCurrentNode().data.GetSinger()); | ||
624 | + ArtistList.Add(thisArtist); | ||
625 | + Miter.Next(); | ||
626 | + }//아티스트리스트에 아티스트가 정렬되어 삽입된다. | ||
627 | + | ||
628 | + | ||
629 | + DoublyIter<MusicType> Miter2(m_List); | ||
630 | + while (Miter2.NotNull()) | ||
631 | + { | ||
632 | + AlbumType thisAlbum(Miter2.GetCurrentNode().data.GetAlbum(), Miter2.GetCurrentNode().data.GetSinger()); | ||
633 | + AlbumList.Add(thisAlbum); | ||
634 | + Miter2.Next(); | ||
635 | + } | ||
636 | + //AlbumList에 앨범추가됨 | ||
637 | + | ||
638 | + DoublyIter<AlbumType> Abiter(AlbumList); //앨범을 해당 앨범과 같은 아티스트를 가진 아티스트 타입의 리스트에 추가한다. | ||
639 | + while (Abiter.NotNull()) | ||
640 | + { | ||
641 | + DoublyIter<ArtistType> Atiter(ArtistList); | ||
642 | + while (Atiter.NotNull()) | ||
643 | + { | ||
644 | + if (Atiter.GetCurrentNode().data.GetArtistName() == Abiter.GetCurrentNode().data.GetArtistName()) | ||
645 | + { | ||
646 | + ArtistType* temp; | ||
647 | + temp = Atiter.GetCurrentPtr(); | ||
648 | + AlbumType thisAlbum = Abiter.GetCurrentNode().data; | ||
649 | + temp->AddListinList(thisAlbum); | ||
650 | + } | ||
651 | + Atiter.Next(); | ||
652 | + } | ||
653 | + Abiter.Next(); | ||
654 | + } | ||
655 | + | ||
656 | + | ||
657 | + } | ||
658 | + RemakeArtistList = false; //리스트를 갱신했으므로 다시만들 필요가 없다. | ||
659 | + //여기서부턴 출력코드 | ||
660 | + DoublyIter<ArtistType> Atiter2(ArtistList); | ||
661 | + while (Atiter2.NotNull()) | ||
662 | + { | ||
663 | + ArtistType *Atptr; | ||
664 | + Atptr = Atiter2.GetCurrentPtr(); | ||
665 | + Atptr->PrintListinList(); | ||
666 | + Atiter2.Next(); | ||
667 | + } | ||
668 | + | ||
669 | + | ||
670 | + | ||
671 | +} | ||
672 | +void Application::SetMusicIndex() | ||
673 | +{ | ||
674 | + int Index = 1; | ||
675 | + DoublyIter<MusicType> Miter(m_List); | ||
676 | + | ||
677 | + while (Miter.NotNull()) | ||
678 | + { | ||
679 | + MusicType* Mptr; | ||
680 | + Mptr = Miter.GetCurrentPtr(); | ||
681 | + Mptr->SetNum(Index); | ||
682 | + Index++; | ||
683 | + Miter.Next(); | ||
684 | + } | ||
685 | + //List의 끝까지 인덱스를 부여한다. 인덱스의 최대값은 MusicList의 길이이다. | ||
686 | + | ||
687 | + | ||
688 | + | ||
689 | +} | ||
690 | +void Application::SearchByIndex(MusicType &indata) | ||
691 | +{ | ||
692 | + DoublyIter<MusicType> Miter(m_List); | ||
693 | + int Index = indata.GetNum(); | ||
694 | + while (Miter.NotNull()) | ||
695 | + { | ||
696 | + if (Index == Miter.GetCurrentNode().data.GetNum()) | ||
697 | + Miter.GetCurrentNode().data.DisplayRecordOnScreen(); | ||
698 | + Miter.Next(); | ||
699 | + } | ||
700 | + | ||
701 | + | ||
702 | +} | ||
703 | + | ||
704 | +void Application::makePlayList() | ||
705 | +{ | ||
706 | + string N; | ||
707 | + PLType PL; | ||
708 | + cout << "재생목록 이름 :"; | ||
709 | + cin >> N; | ||
710 | + PL.setPLname(N); | ||
711 | + PlayLists.Add(PL); | ||
712 | +} | ||
713 | + | ||
714 | + | ||
715 | +void Application::AddMusicInPL() | ||
716 | +{ | ||
717 | + DoublyIter2<PLType> PLiter(PlayLists); | ||
718 | + while (PLiter.NotNull()) | ||
719 | + { | ||
720 | + cout << "재생목록명 : " << PLiter.GetCurrentNode().data.getPLname(); | ||
721 | + cout << endl; | ||
722 | + PLiter.Next(); | ||
723 | + } | ||
724 | + string N; | ||
725 | + cout << "추가하고자 하는 재생목록 선택 : " << endl; | ||
726 | + cin >> N; | ||
727 | + DoublyIter2<PLType> PLiter2(PlayLists); | ||
728 | + PLType* ptr; | ||
729 | + while (PLiter2.NotNull()) | ||
730 | + { | ||
731 | + if (PLiter2.GetCurrentNode().data.getPLname() == N) | ||
732 | + { | ||
733 | + ptr = PLiter2.GetCurrentPtr(); | ||
734 | + DisplayAllMusic(); | ||
735 | + int num = 1; | ||
736 | + while (1) | ||
737 | + { | ||
738 | + cout << "추가하고자 하는 곡의 Index를 입력해주세요 0을 입력하면 그만 추가합니다" << endl; | ||
739 | + cin >> num; | ||
740 | + if (num > m_List.GetLength() || num == 0) | ||
741 | + break; | ||
742 | + DoublyIter2<ManageType> Mgiter(mg_List); | ||
743 | + ManageType* mgPtr; | ||
744 | + while (Mgiter.NotNull()) | ||
745 | + { | ||
746 | + if (Mgiter.GetCurrentNode().data.getIndex() == num) | ||
747 | + { | ||
748 | + mgPtr = Mgiter.GetCurrentPtr(); | ||
749 | + ptr->AddListinList(mgPtr); | ||
750 | + } | ||
751 | + Mgiter.Next(); | ||
752 | + } | ||
753 | + | ||
754 | + } | ||
755 | + } | ||
756 | + PLiter2.Next(); | ||
757 | + } | ||
758 | + | ||
759 | +} | ||
760 | +void Application::PrintPL() | ||
761 | +{ | ||
762 | + DoublyIter2<PLType> PLiter(PlayLists); | ||
763 | + while (PLiter.NotNull()) | ||
764 | + { | ||
765 | + cout << "재생목록명 : " << PLiter.GetCurrentNode().data.getPLname(); | ||
766 | + cout << endl; | ||
767 | + PLiter.Next(); | ||
768 | + } | ||
769 | + string N; | ||
770 | + cout << "재생목록 선택 : " << endl; | ||
771 | + cin >> N; | ||
772 | + DoublyIter2<PLType> PLiter2(PlayLists); | ||
773 | + PLType* ptr; | ||
774 | + while (PLiter2.NotNull()) | ||
775 | + { | ||
776 | + if (PLiter2.GetCurrentNode().data.getPLname() == N) | ||
777 | + { | ||
778 | + ptr = PLiter2.GetCurrentPtr(); | ||
779 | + ptr->Printall(); | ||
780 | + while (1) | ||
781 | + { | ||
782 | + int temp; | ||
783 | + cout << "재생할 곡을 선택해주세요 0을 입력하면 재생목록에서 나갑니다" << endl; | ||
784 | + cin >> temp; | ||
785 | + if (temp == 0) | ||
786 | + break; | ||
787 | + } | ||
788 | + } | ||
789 | + PLiter2.Next(); | ||
790 | + } | ||
791 | + | ||
792 | + | ||
793 | + | ||
794 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/Application.h
0 → 100644
1 | + | ||
2 | +#ifndef _APPLICATION_H | ||
3 | +#define _APPLICATION_H | ||
4 | + | ||
5 | +#include <iostream> | ||
6 | +#include <fstream> | ||
7 | +#include <string> | ||
8 | +#include<sstream> | ||
9 | +using namespace std; | ||
10 | + | ||
11 | + | ||
12 | +#include "MusicType.h" | ||
13 | +#include"SortedLinkedList.h" | ||
14 | +#include"GenreType.h" | ||
15 | +#include"AlbumType.h" | ||
16 | +#include"ArtistType.h" | ||
17 | +#include"ManageType.h" | ||
18 | +#include"UnSortedLinkedList.h" | ||
19 | +#include"PLType.h" | ||
20 | +#define FILENameSIZE 1024 | ||
21 | + | ||
22 | +/** | ||
23 | +* application class for item management simply. | ||
24 | +*/ | ||
25 | +class Application | ||
26 | +{ | ||
27 | +public: | ||
28 | + /** | ||
29 | + * default constructor. | ||
30 | + */ | ||
31 | + Application() | ||
32 | + { | ||
33 | + m_Command = 0; | ||
34 | + RemakeAlbumList = true; | ||
35 | + RemakeArtistList = true; | ||
36 | + RemakeGenreList = true; | ||
37 | + NumofPL = 0; | ||
38 | + | ||
39 | + } | ||
40 | + | ||
41 | + /** | ||
42 | + * destructor. | ||
43 | + */ | ||
44 | + ~Application() | ||
45 | + { | ||
46 | + DoublyIter<ArtistType> Atiter(ArtistList); | ||
47 | + while (Atiter.NotNull()) | ||
48 | + { | ||
49 | + ArtistType* Atptr = Atiter.GetCurrentPtr(); | ||
50 | + Atptr->MakeEmptyListinList(); | ||
51 | + Atiter.Next(); | ||
52 | + } | ||
53 | + m_List.MakeEmpty(); | ||
54 | + GenreList.MakeEmpty(); | ||
55 | + AlbumList.MakeEmpty(); | ||
56 | + }; | ||
57 | + | ||
58 | + /** | ||
59 | + * @brief Program driver. | ||
60 | + * @pre program is started. | ||
61 | + * @post program is finished. | ||
62 | + */ | ||
63 | + void Run(); | ||
64 | + | ||
65 | + /** | ||
66 | + * @brief Display command on screen and get a input from keyboard. | ||
67 | + * @pre none. | ||
68 | + * @post none. | ||
69 | + * @return user's command. | ||
70 | + */ | ||
71 | + int GetCommand(); | ||
72 | + | ||
73 | + /** | ||
74 | + * @brief Add new record into list. | ||
75 | + * @pre list should be initialized. | ||
76 | + * @post new record is added into the list. | ||
77 | + * @return return 1 if this function works well, otherwise 0. | ||
78 | + */ | ||
79 | + int AddMusic(); | ||
80 | + | ||
81 | + /** | ||
82 | + * @brief Display all records in the list on screen. | ||
83 | + * @pre none. | ||
84 | + * @post none. | ||
85 | + */ | ||
86 | + void DisplayAllMusic(); | ||
87 | + | ||
88 | + /** | ||
89 | + * @brief Open a file by file descriptor as an input file. | ||
90 | + * @pre a file for reading is exist. | ||
91 | + * @post open the file for reading. | ||
92 | + * @param fileName a fileName to open for reading. | ||
93 | + * @return return 1 if this function works well, otherwise 0. | ||
94 | + */ | ||
95 | + int OpenInFile(char *fileName); | ||
96 | + | ||
97 | + /** | ||
98 | + * @brief Open a file by file descriptor as an output file. | ||
99 | + * @pre list should be initialized. | ||
100 | + * @post open the file for writing. | ||
101 | + * @param fileName a fileName to open for writing. | ||
102 | + * @return return 1 if this function works well, otherwise 0. | ||
103 | + */ | ||
104 | + int OpenOutFile(char *fileName); | ||
105 | + | ||
106 | + /** | ||
107 | + * @brief Open a file as a read mode, read all data on the file, and set list by the data. | ||
108 | + * @pre The file is not opened. | ||
109 | + * @post list holds all records from the file. | ||
110 | + * @return return 1 if this function works well, otherwise 0. | ||
111 | + */ | ||
112 | + int ReadDataFromFile(); | ||
113 | + | ||
114 | + /** | ||
115 | + * @brief Open a file as a write mode, and write all data into the file, | ||
116 | + * @pre The file is not opened. | ||
117 | + * @post the list is stored in the output file. | ||
118 | + * @return return 1 if this function works well, otherwise 0. | ||
119 | + */ | ||
120 | + int WriteDataToFile(); | ||
121 | + | ||
122 | + /** | ||
123 | +* @brief 객체를 생성 후, 문자열을 입력받는다. | ||
124 | +* @pre 없다. | ||
125 | +* @post SearchByName함수에 문자열이 설정된 객체를 전달한다. | ||
126 | +* @return 없다. | ||
127 | +*/ | ||
128 | + void RetreiveRecordByName(); | ||
129 | + | ||
130 | + /** | ||
131 | + * @brief inData의 이름 부분을 포함하는 문자열을 찾아 출력한다. | ||
132 | + * @pre inData의 이름 부분이 초기화되어있어야 한다. | ||
133 | + * @post inData에 알맞은 항목이 복사된다. | ||
134 | + * @param inData 이름이 설정되어있고 나머지는 비어있는 Musictype | ||
135 | + * @return 없다. | ||
136 | + */ | ||
137 | + void SearchByName(MusicType &inData); | ||
138 | + | ||
139 | + /** | ||
140 | +* @brief 객체를 생성 후, 문자열을 입력받는다. | ||
141 | +* @pre 없다. | ||
142 | +* @post SearchBySinger함수에 문자열이 설정된 객체를 전달한다. | ||
143 | +* @return 없다. | ||
144 | +*/ | ||
145 | + void RetreiveRecordBySinger(); | ||
146 | + | ||
147 | + /** | ||
148 | + * @brief inData의 이름 부분을 포함하는 문자열을 찾아 출력한다. | ||
149 | + * @pre inData의 이름 부분이 초기화되어있어야 한다. | ||
150 | + * @post inData에 알맞은 항목이 복사된다. | ||
151 | + * @param inData 이름이 설정되어있고 나머지는 비어있는 Musictype | ||
152 | + * @return 없다. | ||
153 | + */ | ||
154 | + void SearchBySinger(MusicType &inData); | ||
155 | + | ||
156 | + | ||
157 | + /** | ||
158 | +* @brief 객체를 생성 후, 문자열을 입력받는다. | ||
159 | +* @pre 없다. | ||
160 | +* @post SearchByAlbum함수에 문자열이 설정된 객체를 전달한다. | ||
161 | +* @return 없다. | ||
162 | +*/ | ||
163 | + void RetreiveRecordByAlbum(); | ||
164 | + | ||
165 | + /** | ||
166 | + * @brief inData의 이름 부분을 포함하는 문자열을 찾아 출력한다. | ||
167 | + * @pre inData의 이름 부분이 초기화되어있어야 한다. | ||
168 | + * @post inData에 알맞은 항목이 복사된다. | ||
169 | + * @param inData 이름이 설정되어있고 나머지는 비어있는 Musictype | ||
170 | + * @return 없다. | ||
171 | + */ | ||
172 | + void SearchByAlbum(MusicType &inData); | ||
173 | + /** | ||
174 | +* @brief 객체를 생성 후, 문자열을 입력받는다. | ||
175 | +* @pre 없다. | ||
176 | +* @post SearchByGenre함수에 문자열이 설정된 객체를 전달한다. | ||
177 | +* @return 없다. | ||
178 | +*/ | ||
179 | + void RetreiveRecordByGenre(); | ||
180 | + | ||
181 | + /** | ||
182 | + * @brief inData의 이름 부분을 포함하는 문자열을 찾아 출력한다. | ||
183 | + * @pre inData의 이름 부분이 초기화되어있어야 한다. | ||
184 | + * @post inData에 알맞은 항목이 복사된다. | ||
185 | + * @param inData 이름이 설정되어있고 나머지는 비어있는 Musictype | ||
186 | + * @return 없다. | ||
187 | + */ | ||
188 | + void SearchByGenre(MusicType &inData); | ||
189 | + /** | ||
190 | + * @brief inData의 Index와 같은 Index를 가진 MusicList의 정보를 찾아온다 | ||
191 | + * @pre inData의 Index가 초기화 되어 있어야 한다. | ||
192 | + * @post inData에 알맞은 항목이 복사된다. | ||
193 | + * @param inData Index가 설정되어있고 나머지는 비어있는 Musictype | ||
194 | + * @return 없다. | ||
195 | + */ | ||
196 | + | ||
197 | + void SearchByIndex(MusicType &indata); | ||
198 | + /** | ||
199 | + * @brief 사용자에게 Name을 입력받아 SortedList의 Delete함수에 넘겨주는 역할을 한다. | ||
200 | + * @pre 없다. | ||
201 | + * @post 사용자가 입력한 Name을 가지고 있는 Musictype이 m_List에서 사라진다. | ||
202 | + * @return 없다. | ||
203 | + */ | ||
204 | + | ||
205 | + void Delete(); | ||
206 | + | ||
207 | + /** | ||
208 | + * @brief 사용자에게 Name을 입력받아 SortedList의 Replace함수에 넘겨주는 역할을 한다. | ||
209 | + * @pre 없다. | ||
210 | + * @post 사용자가 입력한 Name을 가지고 있는 MusicType을 다시 입력받아 갱신한다. | ||
211 | + * @return 없다. | ||
212 | + */ | ||
213 | + void Update(); | ||
214 | + /** | ||
215 | + * @brief 최근에 추가된 30곡의 자세한 정보를 화면에 출력 | ||
216 | + * @pre 없다. | ||
217 | + * @post 없다. | ||
218 | + * @return 없다. | ||
219 | + */ | ||
220 | + void DIsplayNewMusic(); | ||
221 | + /** | ||
222 | + * @brief Primary key를 이용해 원하는 음악정보가져온다. | ||
223 | + * @pre 리스트가 초기화되어야함. | ||
224 | + * @post inData에 원하는 곡정보가 담김 | ||
225 | + * @return 찾으면 1, 아니면 0 | ||
226 | + * @param key 곡번호를 찾기위한 int형 변수 | ||
227 | + * @inData 원하는 곡의 정보를 받아오기 위한 변수 | ||
228 | + */ | ||
229 | + bool Search(int key, MusicType& inData); | ||
230 | + /** | ||
231 | + * @brief 장르 리스트에 있는 곡들을 장르에 맞춰 출력 | ||
232 | + * @pre 없다. | ||
233 | + * @post 없다. | ||
234 | + * @return 없다. | ||
235 | + */ | ||
236 | + void DisplayMusicbyGenre(); | ||
237 | + | ||
238 | + /** | ||
239 | +* @brief 객체를 생성 후, 문자열을 입력받는다. | ||
240 | +* @pre 없다. | ||
241 | +* @post SearchByNameNGenre함수에 문자열이 설정된 객체를 전달한다. | ||
242 | +* @return 없다. | ||
243 | +*/ | ||
244 | + void RetreiveRecordByNameNGenre(); | ||
245 | + | ||
246 | + /** | ||
247 | + * @brief inData의 이름 부분을 포함하는 문자열을 찾아 출력한다. | ||
248 | + * @pre inData의 이름 부분이 초기화되어있어야 한다. | ||
249 | + * @post inData에 알맞은 항목이 복사된다. | ||
250 | + * @param inData 이름이 설정되어있고 나머지는 비어있는 Musictype | ||
251 | + * @return 없다. | ||
252 | + */ | ||
253 | + void SearchByNameNGenre(MusicType &inData); | ||
254 | + /** | ||
255 | +* @brief MusicList에 있는 곡을 앨범별로 출력한다. | ||
256 | +* @pre 없다. | ||
257 | +* @post 없다. | ||
258 | +* @return 없다. | ||
259 | +*/ | ||
260 | + void DisplayMusicByAlbum(); | ||
261 | + /** | ||
262 | +* @brief MusicList에 있는 곡을 아티스트별로 나누고, 각 아티스트별 로 앨범을 분류하여 출력한다. | ||
263 | +* @pre 없다. | ||
264 | +* @post 없다. | ||
265 | +* @return 없다. | ||
266 | +*/ | ||
267 | + void DisplayMusicByArtist(); | ||
268 | + /** | ||
269 | +* @brief MusicList에 있는 곡을 Primary Key에 따라 정렬된 순서에 따라 Index를 부여한다 | ||
270 | +* @pre MusicList에 최소한 하나이상의 곡이 있어야한다. | ||
271 | +* @post MusicList의 각 MusicType에 Index가 부여된다 | ||
272 | +* @return 없다. | ||
273 | +*/ | ||
274 | + void SetMusicIndex(); | ||
275 | + /** | ||
276 | +* @brief MusicList의 Music을 분류하는 하위리스트들을 다시 만들기 위한 조건을 충족시킨다. | ||
277 | +* @pre 곡이 추가되거나, 삭제되거나, 변경되어야 한다. | ||
278 | +* @post Remake~~List 형의 변수의 값이 모두 true가 된다. | ||
279 | +* @return 없다. | ||
280 | +*/ | ||
281 | + void RemakeSubList() | ||
282 | + { | ||
283 | + RemakeAlbumList = true; | ||
284 | + RemakeArtistList = true; | ||
285 | + RemakeGenreList = true; | ||
286 | + }; | ||
287 | + | ||
288 | + void makePlayList(); | ||
289 | + | ||
290 | + void AddMusicInPL(); | ||
291 | + | ||
292 | + void PrintPL(); | ||
293 | + | ||
294 | +private: | ||
295 | + ifstream m_InFile; ///< input file descriptor. | ||
296 | + ofstream m_OutFile; ///< output file descriptor. | ||
297 | + SortedLinkedList<MusicType> m_List; /// 노래 리스트 | ||
298 | + UnSortedLinkedList<ManageType> mg_List; | ||
299 | + int m_Command; ///< current command number. | ||
300 | + SortedLinkedList<AlbumType> AlbumList; //앨범을 분류하기 위한 앨범리스트 | ||
301 | + SortedLinkedList<ArtistType> ArtistList; //아티스트를 분류하기 위한 아티스트리스트 | ||
302 | + SortedLinkedList <string> GenreList; //장르를 분류하기 위한 장르 리스트 | ||
303 | + UnSortedLinkedList<PLType> PlayLists; | ||
304 | + //아래의 변수들은 각 하위 리스트를 다시만들어야 할지 판별하는 변수이다. | ||
305 | + bool RemakeAlbumList; | ||
306 | + bool RemakeArtistList; | ||
307 | + bool RemakeGenreList; | ||
308 | + int NumofPL; | ||
309 | +}; | ||
310 | + | ||
311 | + | ||
312 | + | ||
313 | +#endif // _APPLICATION_H | ||
314 | + | ||
315 | + |
Project/ArtistType.cpp
0 → 100644
1 | + | ||
2 | +#include"ArtistType.h" | ||
3 | + | ||
4 | +void ArtistType::PrintListinList() | ||
5 | +{ | ||
6 | + DoublyIter<AlbumType> Abiter(AlbumList); | ||
7 | + cout << "\t ----------------" << endl; | ||
8 | + cout << "\t ƼƮ : " << ArtistName << endl; | ||
9 | + while (Abiter.NotNull()) | ||
10 | + { | ||
11 | + cout << "\tٹ" << Abiter.GetCurrentNode().data.GetAlbumName() << endl; | ||
12 | + Abiter.Next(); | ||
13 | + } | ||
14 | +} | ||
15 | + | ||
16 | +ArtistType::ArtistType(const ArtistType& data) | ||
17 | +{ | ||
18 | + ArtistName = data.ArtistName; | ||
19 | + AlbumList = data.AlbumList; | ||
20 | + | ||
21 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/ArtistType.h
0 → 100644
1 | +#pragma once | ||
2 | +#include"AlbumType.h" | ||
3 | +using namespace std; | ||
4 | + | ||
5 | +class ArtistType { | ||
6 | +public: | ||
7 | + ArtistType() | ||
8 | + { | ||
9 | + ArtistName = ""; | ||
10 | + } | ||
11 | + ; //기본 생성자 | ||
12 | + ~ArtistType() | ||
13 | + { | ||
14 | + AlbumList.MakeEmpty(); | ||
15 | + } | ||
16 | + ; //기본 소멸자 | ||
17 | + ArtistType(const ArtistType& data); | ||
18 | + /** | ||
19 | +* @brief Get ArtistName | ||
20 | +* @pre ArtistName is set | ||
21 | +* @post x | ||
22 | +* @return ArtistName | ||
23 | +*/ | ||
24 | + string GetArtistName() | ||
25 | + { | ||
26 | + return ArtistName; | ||
27 | + }; | ||
28 | + /** | ||
29 | +* @brief set ArtistName | ||
30 | +* @pre x | ||
31 | +* @post ArtistName is set | ||
32 | +*/ | ||
33 | + void SetArtistName(string Name) | ||
34 | + { | ||
35 | + ArtistName = Name; | ||
36 | + }; | ||
37 | + /** | ||
38 | +* @brief 비교 연산자 | ||
39 | +* @pre 비교하려는 두 아티스트타입이 초기화되어 있어야한다 | ||
40 | +* @post x | ||
41 | +* @param data 비교하려는 아티스트타입 | ||
42 | +* @return 좌변이크면 false, 우변이크면 true | ||
43 | +*/ | ||
44 | + bool operator<(ArtistType data) | ||
45 | + { | ||
46 | + return (ArtistName < data.GetArtistName()); | ||
47 | + }; | ||
48 | + /** | ||
49 | +* @brief 비교 연산자 | ||
50 | +* @pre 비교하려는 두 아티스트타입이 초기화되어 있어야한다 | ||
51 | +* @post x | ||
52 | +* @param data 비교하려는 아티스트타입 | ||
53 | +* @return 좌변이크면 true, 우변이크면 false | ||
54 | +*/ | ||
55 | + bool operator>(ArtistType data) | ||
56 | + { | ||
57 | + return (ArtistName > data.GetArtistName()); | ||
58 | + }; | ||
59 | + /** | ||
60 | +* @brief 등위 연산자 | ||
61 | +* @pre 비교하려는 두 아티스트타입이 초기화되어 있어야한다 | ||
62 | +* @post x | ||
63 | +* @param data 비교하려는 아티스트타입 | ||
64 | +* @return 두 항이 같으면 true 아니면 false | ||
65 | +*/ | ||
66 | + bool operator==(ArtistType data) | ||
67 | + { | ||
68 | + if (ArtistName == data.GetArtistName()) | ||
69 | + return true; | ||
70 | + else | ||
71 | + return false; | ||
72 | + }; | ||
73 | + /** | ||
74 | +* @brief 대입 연산자 | ||
75 | +* @pre 패러미터로 넘어오는 Artisttype이 초기화되어있어야한다. | ||
76 | +* @post this가 data와 같아진다 | ||
77 | +* @param data 대입하려는 아티스트타입 | ||
78 | +* @return *this | ||
79 | +*/ | ||
80 | + ArtistType operator=(const ArtistType& data) | ||
81 | + { | ||
82 | + ArtistName = data.ArtistName; | ||
83 | + AlbumList = data.AlbumList; | ||
84 | + return *this; | ||
85 | + }; | ||
86 | + /** | ||
87 | +* @brief 리스트안의 리스트에 원소를 추가한다 | ||
88 | +* @pre x | ||
89 | +* @post AlbumList에 앨범이 추가된다. | ||
90 | +* @param A 추가하려는 앨범타입 | ||
91 | +*/ | ||
92 | + void AddListinList(AlbumType &A) | ||
93 | + { | ||
94 | + AlbumList.Add(A); | ||
95 | + }; | ||
96 | + /** | ||
97 | +* @brief 리스트 안의 리스트의 내용을 출력한다. | ||
98 | +* @pre 앨범리스트가 초기화되어 있어야 한다. | ||
99 | +* @post x | ||
100 | +*/ | ||
101 | + void PrintListinList() ; | ||
102 | + | ||
103 | + void MakeEmptyListinList() | ||
104 | + { | ||
105 | + AlbumList.MakeEmpty(); | ||
106 | + } | ||
107 | +private: | ||
108 | + SortedLinkedList<AlbumType> AlbumList; //한 아티스트가 가지는 앨범 리스트 | ||
109 | + string ArtistName; | ||
110 | + | ||
111 | +}; |
Project/DoublyIter.h
0 → 100644
1 | +#pragma once | ||
2 | +#ifndef _SORTED_LINKED_LIST_H | ||
3 | +#define _SORTED_LINKED_LIST_H | ||
4 | +#include"SortedLinkedList.h" | ||
5 | + | ||
6 | + | ||
7 | +template<typename T> | ||
8 | +class SortedLinkedList; | ||
9 | + | ||
10 | +template<typename T> | ||
11 | +struct NodeType; | ||
12 | + | ||
13 | + | ||
14 | + | ||
15 | +template<typename T> | ||
16 | +class DoublyIter { | ||
17 | + friend class SortedLinkedList<T>; | ||
18 | + | ||
19 | +private: | ||
20 | + const SortedLinkedList<T>& m_List; | ||
21 | + NodeType<T>* CurPointer; | ||
22 | +public: | ||
23 | + DoublyIter(const SortedLinkedList<T>& list) : m_List(list), CurPointer(list.m_pList) | ||
24 | + {} | ||
25 | + /** | ||
26 | + * @brief 현재 노드를 가리키는 포인터가 null인지 아닌지 판단하는 메서드. | ||
27 | + * @pre Iterator has been initialized. | ||
28 | + * @post None. | ||
29 | + * @return nullptr true, otherwise false. | ||
30 | + */ | ||
31 | + bool NotNull(); | ||
32 | + | ||
33 | + /** | ||
34 | + * @brief 현재 노드 포인터의 다음 노드가 null인지 아닌지 판단하는 메서드. | ||
35 | + * @pre Iterator has been initialized. | ||
36 | + * @post None. | ||
37 | + * @return nullptr true, otherwise false. | ||
38 | + */ | ||
39 | + bool NextNotNull(); | ||
40 | + /** | ||
41 | + * @brief 현재 노드 포인터의 이전 노드가 null인지 아닌지 판단하는 메서드. | ||
42 | + * @pre Iterator has been initialized. | ||
43 | + * @post None. | ||
44 | + * @return nullptr true, otherwise false. | ||
45 | + */ | ||
46 | + bool PrevNotNull(); | ||
47 | + /** | ||
48 | + * @brief Get first data of the list. | ||
49 | + * @pre Iterator has been initialized. | ||
50 | + * @post Current pointer is moved to the first node. | ||
51 | + * @return Return first data of the list. | ||
52 | + */ | ||
53 | + T First(); | ||
54 | + | ||
55 | + /** | ||
56 | + * @brief Get next data of the current pointer. | ||
57 | + * @pre Iterator has been initialized. | ||
58 | + * @post Current pointer is moved to the next node. | ||
59 | + * @return Return next data of the list. | ||
60 | + */ | ||
61 | + T Next(); | ||
62 | + | ||
63 | + /** | ||
64 | + * @brief Get current data of the list and go to the next node. 현재 노드. 객체반환은 return by value | ||
65 | + * @pre Iterator has been initialized. | ||
66 | + * @post Current pointer is moved to next node. | ||
67 | + * @return Return current data of the list. | ||
68 | + */ | ||
69 | + NodeType<T> GetCurrentNode(); | ||
70 | + /** | ||
71 | + * @brief 현재 노드의 data의 주소값을 반환하는 함수 | ||
72 | + * @pre Iterator has been initialized. | ||
73 | + * @post x | ||
74 | + * @return Return current data's address | ||
75 | + */ | ||
76 | + T* GetCurrentPtr(); | ||
77 | + /** | ||
78 | + * @brief 마지막 데이터의 포인터를 받는다. | ||
79 | + * @pre Iterator has been initialized. | ||
80 | + * @post x | ||
81 | + * @return Return last data of the list. | ||
82 | + */ | ||
83 | + T Last(); | ||
84 | + /** | ||
85 | + * @brief Curpointer의 이전 노드로 간다 | ||
86 | + * @pre Iterator has been initialized. | ||
87 | + * @post 이전 노드로 포인터가 이동한다 | ||
88 | + * @return Return Prev data of the list. | ||
89 | + */ | ||
90 | + T Prev(); | ||
91 | + | ||
92 | + | ||
93 | + | ||
94 | +}; | ||
95 | + | ||
96 | + | ||
97 | + | ||
98 | +// 현재 원소가 null인지 검사 | ||
99 | +template <typename T> | ||
100 | +bool DoublyIter<T>::NotNull() { | ||
101 | + if (CurPointer == NULL) { | ||
102 | + return false; | ||
103 | + } | ||
104 | + else return true; | ||
105 | +} | ||
106 | + | ||
107 | +// 다음 원소가 null인지 검사 | ||
108 | +template <typename T> | ||
109 | +bool DoublyIter<T>::NextNotNull() { | ||
110 | + if (CurPointer->next == NULL) { | ||
111 | + | ||
112 | + return false; | ||
113 | + } | ||
114 | + else | ||
115 | + return true; | ||
116 | +} | ||
117 | + | ||
118 | +template<typename T> | ||
119 | +bool DoublyIter<T>::PrevNotNull() | ||
120 | +{ | ||
121 | + if (CurPointer->Prev == NULL) | ||
122 | + return false; | ||
123 | + else | ||
124 | + return true; | ||
125 | + | ||
126 | +} | ||
127 | +// 첫 번째 node | ||
128 | +template <typename T> | ||
129 | +T DoublyIter<T>::First() { | ||
130 | + if (!m_List.IsEmpty()) { | ||
131 | + CurPointer = m_List.m_pFirst; | ||
132 | + return CurPointer->data; | ||
133 | + } | ||
134 | +} | ||
135 | + | ||
136 | +// 다음 node로 이동 후 item을 return. | ||
137 | +template <typename T> | ||
138 | +T DoublyIter<T>::Next() { | ||
139 | + T output = CurPointer->data; | ||
140 | + if (NotNull()) { | ||
141 | + CurPointer = CurPointer->next; | ||
142 | + } | ||
143 | + return output; | ||
144 | +} | ||
145 | +template<typename T> | ||
146 | +T DoublyIter<T>::Last() | ||
147 | +{ | ||
148 | + if (!m_List.IsEmpty()) { | ||
149 | + CurPointer = m_List.m_pLast; | ||
150 | + return CurPointer -> data; | ||
151 | + } | ||
152 | + | ||
153 | + | ||
154 | +} | ||
155 | +template<typename T> | ||
156 | +T DoublyIter<T>::Prev() | ||
157 | +{ | ||
158 | + T output = CurPointer->data; | ||
159 | + if (NotNull()) { | ||
160 | + CurPointer = CurPointer->prev; | ||
161 | + } | ||
162 | + return output; | ||
163 | + | ||
164 | + | ||
165 | +} | ||
166 | +// 현재 node를 return | ||
167 | +template <typename T> | ||
168 | +NodeType<T> DoublyIter<T>::GetCurrentNode() { | ||
169 | + if (CurPointer != NULL) { | ||
170 | + return *CurPointer; | ||
171 | + } | ||
172 | +} | ||
173 | +template<typename T> | ||
174 | +T* DoublyIter<T>::GetCurrentPtr() | ||
175 | +{ | ||
176 | + if (CurPointer != NULL) | ||
177 | + { | ||
178 | + return &(CurPointer->data); | ||
179 | + } | ||
180 | + | ||
181 | +} | ||
182 | + | ||
183 | +#endif // !_DOUBLY_ITER_H | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/DoublyIter2.h
0 → 100644
1 | +#pragma once | ||
2 | +#ifndef _UN_SORTED_LINKED_LIST_H | ||
3 | +#define _UN_SORTED_LINKED_LIST_H | ||
4 | +#include"UnSortedLinkedList.h" | ||
5 | + | ||
6 | + | ||
7 | +template<typename T> | ||
8 | +class UnSortedLinkedList; | ||
9 | + | ||
10 | +template<typename T> | ||
11 | +struct NodeType2; | ||
12 | + | ||
13 | + | ||
14 | + | ||
15 | +template<typename T> | ||
16 | +class DoublyIter2 { | ||
17 | + friend class UnSortedLinkedList<T>; | ||
18 | + | ||
19 | +private: | ||
20 | + const UnSortedLinkedList<T>& m_List; | ||
21 | + NodeType2<T>* CurPointer; | ||
22 | +public: | ||
23 | + DoublyIter2(const UnSortedLinkedList<T>& list) : m_List(list), CurPointer(list.m_pList) | ||
24 | + {} | ||
25 | + /** | ||
26 | + * @brief 현재 노드를 가리키는 포인터가 null인지 아닌지 판단하는 메서드. | ||
27 | + * @pre Iterator has been initialized. | ||
28 | + * @post None. | ||
29 | + * @return nullptr true, otherwise false. | ||
30 | + */ | ||
31 | + bool NotNull(); | ||
32 | + | ||
33 | + /** | ||
34 | + * @brief 현재 노드 포인터의 다음 노드가 null인지 아닌지 판단하는 메서드. | ||
35 | + * @pre Iterator has been initialized. | ||
36 | + * @post None. | ||
37 | + * @return nullptr true, otherwise false. | ||
38 | + */ | ||
39 | + bool NextNotNull(); | ||
40 | + /** | ||
41 | + * @brief 현재 노드 포인터의 이전 노드가 null인지 아닌지 판단하는 메서드. | ||
42 | + * @pre Iterator has been initialized. | ||
43 | + * @post None. | ||
44 | + * @return nullptr true, otherwise false. | ||
45 | + */ | ||
46 | + bool PrevNotNull(); | ||
47 | + /** | ||
48 | + * @brief Get first data of the list. | ||
49 | + * @pre Iterator has been initialized. | ||
50 | + * @post Current pointer is moved to the first node. | ||
51 | + * @return Return first data of the list. | ||
52 | + */ | ||
53 | + T First(); | ||
54 | + | ||
55 | + /** | ||
56 | + * @brief Get next data of the current pointer. | ||
57 | + * @pre Iterator has been initialized. | ||
58 | + * @post Current pointer is moved to the next node. | ||
59 | + * @return Return next data of the list. | ||
60 | + */ | ||
61 | + T Next(); | ||
62 | + | ||
63 | + /** | ||
64 | + * @brief Get current data of the list and go to the next node. 현재 노드. 객체반환은 return by value | ||
65 | + * @pre Iterator has been initialized. | ||
66 | + * @post Current pointer is moved to next node. | ||
67 | + * @return Return current data of the list. | ||
68 | + */ | ||
69 | + NodeType2<T> GetCurrentNode(); | ||
70 | + /** | ||
71 | + * @brief 현재 노드의 data의 주소값을 반환하는 함수 | ||
72 | + * @pre Iterator has been initialized. | ||
73 | + * @post x | ||
74 | + * @return Return current data's address | ||
75 | + */ | ||
76 | + T* GetCurrentPtr(); | ||
77 | + /** | ||
78 | + * @brief 마지막 데이터의 포인터를 받는다. | ||
79 | + * @pre Iterator has been initialized. | ||
80 | + * @post x | ||
81 | + * @return Return last data of the list. | ||
82 | + */ | ||
83 | + T Last(); | ||
84 | + /** | ||
85 | + * @brief Curpointer의 이전 노드로 간다 | ||
86 | + * @pre Iterator has been initialized. | ||
87 | + * @post 이전 노드로 포인터가 이동한다 | ||
88 | + * @return Return Prev data of the list. | ||
89 | + */ | ||
90 | + T Prev(); | ||
91 | + | ||
92 | + | ||
93 | + | ||
94 | +}; | ||
95 | + | ||
96 | + | ||
97 | + | ||
98 | +// 현재 원소가 null인지 검사 | ||
99 | +template <typename T> | ||
100 | +bool DoublyIter2<T>::NotNull() { | ||
101 | + if (CurPointer == NULL) { | ||
102 | + return false; | ||
103 | + } | ||
104 | + else return true; | ||
105 | +} | ||
106 | + | ||
107 | +// 다음 원소가 null인지 검사 | ||
108 | +template <typename T> | ||
109 | +bool DoublyIter2<T>::NextNotNull() { | ||
110 | + if (CurPointer->next == NULL) { | ||
111 | + | ||
112 | + return false; | ||
113 | + } | ||
114 | + else | ||
115 | + return true; | ||
116 | +} | ||
117 | + | ||
118 | +template<typename T> | ||
119 | +bool DoublyIter2<T>::PrevNotNull() | ||
120 | +{ | ||
121 | + if (CurPointer->Prev == NULL) | ||
122 | + return false; | ||
123 | + else | ||
124 | + return true; | ||
125 | + | ||
126 | +} | ||
127 | +// 첫 번째 node | ||
128 | +template <typename T> | ||
129 | +T DoublyIter2<T>::First() { | ||
130 | + if (!m_List.IsEmpty()) { | ||
131 | + CurPointer = m_List.m_pFirst; | ||
132 | + return CurPointer->data; | ||
133 | + } | ||
134 | +} | ||
135 | + | ||
136 | +// 다음 node로 이동 후 item을 return. | ||
137 | +template <typename T> | ||
138 | +T DoublyIter2<T>::Next() { | ||
139 | + T output = CurPointer->data; | ||
140 | + if (NotNull()) { | ||
141 | + CurPointer = CurPointer->next; | ||
142 | + } | ||
143 | + return output; | ||
144 | +} | ||
145 | +template<typename T> | ||
146 | +T DoublyIter2<T>::Last() | ||
147 | +{ | ||
148 | + if (!m_List.IsEmpty()) { | ||
149 | + CurPointer = m_List.m_pLast; | ||
150 | + return CurPointer->data; | ||
151 | + } | ||
152 | + | ||
153 | + | ||
154 | +} | ||
155 | +template<typename T> | ||
156 | +T DoublyIter2<T>::Prev() | ||
157 | +{ | ||
158 | + T output = CurPointer->data; | ||
159 | + if (NotNull()) { | ||
160 | + CurPointer = CurPointer->pre; | ||
161 | + } | ||
162 | + return output; | ||
163 | + | ||
164 | + | ||
165 | +} | ||
166 | +// 현재 node를 return | ||
167 | +template <typename T> | ||
168 | +NodeType2<T> DoublyIter2<T>::GetCurrentNode() { | ||
169 | + if (CurPointer != NULL) { | ||
170 | + return *CurPointer; | ||
171 | + } | ||
172 | +} | ||
173 | +template<typename T> | ||
174 | +T* DoublyIter2<T>::GetCurrentPtr() | ||
175 | +{ | ||
176 | + if (CurPointer != NULL) | ||
177 | + { | ||
178 | + return &(CurPointer->data); | ||
179 | + } | ||
180 | + | ||
181 | +} | ||
182 | + | ||
183 | +#endif // !_DOUBLY_ITER2_H | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/GenreType.h
0 → 100644
1 | +#pragma once | ||
2 | +#include<iostream> | ||
3 | +#include<string> | ||
4 | +#include"SortedLinkedList.h" | ||
5 | +#include"SimplifiedType.h" | ||
6 | +using namespace std; | ||
7 | +/** | ||
8 | +* @brief 과제 1에서 이 클래스는 쓰이지 않는다. | ||
9 | + | ||
10 | +*/ | ||
11 | +class GenreType //현재 이 장르타입은 쓰지 않는다. | ||
12 | +{ | ||
13 | +public: | ||
14 | + GenreType() | ||
15 | + { | ||
16 | + G_num = -1; | ||
17 | + G_name = ""; | ||
18 | + } //기본 생성자 | ||
19 | + | ||
20 | + ~GenreType() | ||
21 | + { | ||
22 | + | ||
23 | + } //기본 소멸자 | ||
24 | + | ||
25 | + /** | ||
26 | + * @brief Get Genre | ||
27 | + * @pre Genre is set. | ||
28 | + * @post none. | ||
29 | + * @return Genre; | ||
30 | +*/ | ||
31 | + string GetGenre() | ||
32 | + { | ||
33 | + return G_name; | ||
34 | + } | ||
35 | + /** | ||
36 | + * @brief Get song Number | ||
37 | + * @pre song Name is set. | ||
38 | + * @post none. | ||
39 | + * @return song number | ||
40 | +*/ | ||
41 | + int GetNum() | ||
42 | + { | ||
43 | + return G_num; | ||
44 | + } | ||
45 | + /** | ||
46 | + * @brief set song number | ||
47 | + * @pre x | ||
48 | + * @post song number is set | ||
49 | + * @param num song number | ||
50 | +*/ | ||
51 | + void SetNum(int num) | ||
52 | + { | ||
53 | + G_num = num; | ||
54 | + } | ||
55 | + /** | ||
56 | + * @brief set genre | ||
57 | + * @pre x | ||
58 | + * @post genre is set | ||
59 | + * @param Genre Genre | ||
60 | +*/ | ||
61 | + void SetGenre(string Genre) | ||
62 | + { | ||
63 | + G_name = Genre; | ||
64 | + } | ||
65 | + /** | ||
66 | +* @brief 두 SimplifiedType의 Primary key가 같은지 비교함 | ||
67 | +* @pre 비교하고자 하는 SimplifiedType이 초기화 되어있어야함 | ||
68 | +* @post x | ||
69 | +* @param data 비교하고자 하는 데이터 | ||
70 | +* @return 같을경우 true, 다를경우 false | ||
71 | +*/ | ||
72 | + bool operator==(GenreType data) | ||
73 | + { | ||
74 | + | ||
75 | + if (this->GetNum() == data.GetNum()) | ||
76 | + return true; | ||
77 | + else | ||
78 | + return false; | ||
79 | + } | ||
80 | + /** | ||
81 | +* @brief 두 SimplifiedType의 Primary key의 크기를 비교함 | ||
82 | +* @pre 비교하고자 하는 SimplifiedType이 초기화 되어있어야함 | ||
83 | +* @post x | ||
84 | +* @param data 비교하고자 하는 데이터 | ||
85 | +* @return 좌변이 클경우 true 작을경우 false | ||
86 | + | ||
87 | +*/ | ||
88 | + bool operator>(GenreType data) | ||
89 | + { | ||
90 | + if (this->GetNum() > data.GetNum()) | ||
91 | + return true; | ||
92 | + else | ||
93 | + return false; | ||
94 | + } | ||
95 | + /** | ||
96 | +* @brief 두 SimplifiedType의 Primary key의 크기를 비교함 | ||
97 | +* @pre 비교하고자 하는 SimplifiedType이 초기화 되어있어야함 | ||
98 | +* @post x | ||
99 | +* @param data 비교하고자 하는 데이터 | ||
100 | +* @return 우변이 클경우 true 작을경우 false | ||
101 | +*/ | ||
102 | + bool operator<(GenreType data) | ||
103 | + { | ||
104 | + if (this->GetNum() < data.GetNum()) | ||
105 | + return true; | ||
106 | + else | ||
107 | + return false; | ||
108 | + | ||
109 | + } | ||
110 | + /** | ||
111 | +* @brief GenreList안에 Simplified 타입을 넣는 함수 | ||
112 | +* @pre x | ||
113 | +* @post 현재 GenreList에 Simplified 타입이 추가된다 | ||
114 | +* @param 추가하고자 하는 데이터 | ||
115 | +*/ | ||
116 | + void addListinGenre(SimplifiedType in) | ||
117 | + { | ||
118 | + G_List.Add(in); | ||
119 | + } | ||
120 | + /** | ||
121 | +* @brief 현 GenreList안의 모든 데이터를 출력하는함수 | ||
122 | +* @pre GenreList안의 원소가 초기화 되어있어야함 | ||
123 | +* @post x | ||
124 | +*/ | ||
125 | + void PrintAll() | ||
126 | + { | ||
127 | + | ||
128 | + | ||
129 | + | ||
130 | + | ||
131 | + } | ||
132 | + | ||
133 | + | ||
134 | + | ||
135 | + | ||
136 | +private: | ||
137 | + int G_num; //장르 넘버 = Primary Key | ||
138 | + string G_name; //장르 명 | ||
139 | + SortedLinkedList<SimplifiedType> G_List; //각 장르별 장르리스트 | ||
140 | +}; | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/ManageType.h
0 → 100644
1 | +#pragma once | ||
2 | +#include"MusicType.h" | ||
3 | + | ||
4 | + | ||
5 | +class ManageType { | ||
6 | +private: | ||
7 | + string Pkey; | ||
8 | + int played; | ||
9 | + int Index; | ||
10 | + string name; | ||
11 | + string artist; | ||
12 | +public: | ||
13 | + ManageType() { | ||
14 | + Pkey = ""; | ||
15 | + played = 0; | ||
16 | + Index = 0; | ||
17 | + }; | ||
18 | + ~ManageType() {}; | ||
19 | + void setPkey(string key) | ||
20 | + { | ||
21 | + Pkey = key; | ||
22 | + } | ||
23 | + void setIndex(int I) | ||
24 | + { | ||
25 | + Index = I; | ||
26 | + } | ||
27 | + void IncreasePlayed() | ||
28 | + { | ||
29 | + played++; | ||
30 | + } | ||
31 | + void setName(string N) | ||
32 | + { | ||
33 | + name = N; | ||
34 | + } | ||
35 | + void setArtist(string A) | ||
36 | + { | ||
37 | + artist = A; | ||
38 | + } | ||
39 | + string getArtist() | ||
40 | + { | ||
41 | + return artist; | ||
42 | + } | ||
43 | + string getPkey() | ||
44 | + { | ||
45 | + return Pkey; | ||
46 | + } | ||
47 | + int getPlayed() | ||
48 | + { | ||
49 | + return played; | ||
50 | + } | ||
51 | + int getIndex() | ||
52 | + { | ||
53 | + return Index; | ||
54 | + } | ||
55 | + string getName() | ||
56 | + { | ||
57 | + return name; | ||
58 | + } | ||
59 | + | ||
60 | + void PrintNameNArtist() | ||
61 | + { | ||
62 | + cout << "\t°î¸í : " << name << endl; | ||
63 | + cout << "\t¾ÆÆ¼½ºÆ® : " << artist << endl << endl; | ||
64 | + } | ||
65 | + void PrintNameNIndex() | ||
66 | + { | ||
67 | + cout << "\t°î¸í : " << name << endl; | ||
68 | + cout << "\tIndex : " << Index << endl << endl; | ||
69 | + } | ||
70 | + | ||
71 | +}; | ||
72 | + |
Project/MusicType.cpp
0 → 100644
1 | + | ||
2 | +#include "MusicType.h" | ||
3 | + | ||
4 | + | ||
5 | + | ||
6 | + | ||
7 | +// Ǻ | ||
8 | +// Set student song Name from keyboard. | ||
9 | +void MusicType::SetNameFromKB() | ||
10 | +{ | ||
11 | + | ||
12 | + cout << "\tsong Name : "; | ||
13 | + cin >> Name; | ||
14 | + | ||
15 | +} | ||
16 | + | ||
17 | + | ||
18 | +// Set Singer Name from keyboard. | ||
19 | +void MusicType::SetSingerFromKB() | ||
20 | +{ | ||
21 | + | ||
22 | + cout << "\tSinger : "; | ||
23 | + cin >> Singer; | ||
24 | + | ||
25 | +} | ||
26 | + | ||
27 | + | ||
28 | +// Set Album Name from keyboard. | ||
29 | +void MusicType::SetAlbumFromKB() | ||
30 | +{ | ||
31 | + | ||
32 | + cout << "\tAlbum : "; | ||
33 | + cin >> Album; | ||
34 | + | ||
35 | +} | ||
36 | +// Set Genre from keyboard | ||
37 | +void MusicType::SetGenreFromKB() | ||
38 | +{ | ||
39 | + | ||
40 | + cout << "\tGenre : "; | ||
41 | + cin >> Genre; | ||
42 | + | ||
43 | + | ||
44 | +} | ||
45 | + | ||
46 | +// Set Lyrics from keyboard | ||
47 | +void MusicType::SetLyricsFromKB() | ||
48 | +{ | ||
49 | + cin.ignore(); | ||
50 | + cout << "\tLyrics : "; | ||
51 | + getline(cin, Lyrics); | ||
52 | +} | ||
53 | +void MusicType::SetNumFromKB() | ||
54 | +{ | ||
55 | + cout << "\tNumber : "; | ||
56 | + cin >> Num; | ||
57 | +} | ||
58 | + | ||
59 | + | ||
60 | +// Set student record from keyboard. | ||
61 | +void MusicType::SetInfoFromKB() | ||
62 | +{ | ||
63 | + //SetNumFromKB(); | ||
64 | + SetNameFromKB(); | ||
65 | + SetSingerFromKB(); | ||
66 | + SetAlbumFromKB(); | ||
67 | + SetGenreFromKB(); | ||
68 | + SetLyricsFromKB(); | ||
69 | + SetPkey(); | ||
70 | +} | ||
71 | + | ||
72 | + | ||
73 | +// Read a record from file. | ||
74 | +int MusicType::ReadDataFromFile(ifstream& fin) | ||
75 | +{ | ||
76 | + fin >> Name; | ||
77 | + fin >> Singer; | ||
78 | + fin >> Album; | ||
79 | + fin >> Genre; | ||
80 | + getline(fin, Lyrics); | ||
81 | + return 1; | ||
82 | +}; | ||
83 | + | ||
84 | + | ||
85 | +// Write a record into file. | ||
86 | +int MusicType::WriteDataToFile(ofstream& fout) | ||
87 | +{ | ||
88 | + fout << endl; | ||
89 | + fout << Name << " "; | ||
90 | + fout << Singer << " "; | ||
91 | + fout << Album << " "; | ||
92 | + fout << Lyrics << " "; | ||
93 | + | ||
94 | + return 1; | ||
95 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/MusicType.h
0 → 100644
1 | + | ||
2 | +#ifndef _MusicType_H | ||
3 | +#define _MusicType_H | ||
4 | + | ||
5 | +#include <iostream> | ||
6 | +#include <fstream> | ||
7 | +#include <string> | ||
8 | + | ||
9 | +using namespace std; | ||
10 | + | ||
11 | + | ||
12 | + | ||
13 | + | ||
14 | +/** | ||
15 | +* item information class. | ||
16 | +*/ | ||
17 | +class MusicType | ||
18 | +{ | ||
19 | +public: | ||
20 | + /** | ||
21 | + * default constructor. | ||
22 | + */ | ||
23 | + MusicType() | ||
24 | + { | ||
25 | + Num = -1; | ||
26 | + Name = ""; | ||
27 | + Singer = ""; | ||
28 | + Album = ""; | ||
29 | + Genre = ""; | ||
30 | + Lyrics = ""; | ||
31 | + } | ||
32 | + | ||
33 | + /** | ||
34 | + * destructor. | ||
35 | + */ | ||
36 | + ~MusicType() {} | ||
37 | + /** | ||
38 | + * @brief Get song Name | ||
39 | + * @pre song Name is set. | ||
40 | + * @post none. | ||
41 | + * @return song Name; | ||
42 | +*/ | ||
43 | + int GetNum() | ||
44 | + { | ||
45 | + return Num; | ||
46 | + } | ||
47 | + /** | ||
48 | + * @brief Get song Name | ||
49 | + * @pre song Name is set. | ||
50 | + * @post none. | ||
51 | + * @return song Name; | ||
52 | + */ | ||
53 | + string GetName() | ||
54 | + { | ||
55 | + return Name; | ||
56 | + } | ||
57 | + | ||
58 | + /** | ||
59 | + * @brief Get Singer Name. | ||
60 | + * @pre Singer Name is set. | ||
61 | + * @post none. | ||
62 | + * @return Singer Name. | ||
63 | + */ | ||
64 | + string GetSinger() | ||
65 | + { | ||
66 | + return Singer; | ||
67 | + } | ||
68 | + | ||
69 | + /** | ||
70 | + * @brief Get Album Name | ||
71 | + * @pre Album Name is set. | ||
72 | + * @post none. | ||
73 | + * @return Album Name. | ||
74 | + */ | ||
75 | + string GetAlbum() | ||
76 | + { | ||
77 | + return Album; | ||
78 | + } | ||
79 | + /** | ||
80 | + * @brief Get Genre | ||
81 | + * @pre Genre is set. | ||
82 | + * @post none. | ||
83 | + * @return Genre. | ||
84 | + */ | ||
85 | + string GetGenre() | ||
86 | + { | ||
87 | + return Genre; | ||
88 | + } | ||
89 | + /** | ||
90 | + * @brief Get Lyrics | ||
91 | + * @pre Lyrics is set. | ||
92 | + * @post none. | ||
93 | + * @return Lyrics. | ||
94 | + */ | ||
95 | + string GetLyrics() | ||
96 | + { | ||
97 | + return Lyrics; | ||
98 | + } | ||
99 | + /** | ||
100 | + * @brief Get Pkey | ||
101 | + * @pre Pkey is set. | ||
102 | + * @post none. | ||
103 | + * @return Pkey | ||
104 | + */ | ||
105 | + string GetPkey() | ||
106 | + { | ||
107 | + return Pkey; | ||
108 | + } | ||
109 | + /** | ||
110 | + * @brief Set song Name | ||
111 | + * @pre none. | ||
112 | + * @post song Name is set. | ||
113 | + * @param s_Name song Name | ||
114 | + */ | ||
115 | + void SetName(string s_Name) | ||
116 | + { | ||
117 | + Name = s_Name; | ||
118 | + } | ||
119 | + /** | ||
120 | +* @brief Set song Name | ||
121 | +* @pre none. | ||
122 | +* @post song Name is set. | ||
123 | +* @param s_Name song Name | ||
124 | +*/ | ||
125 | + void SetNum(int s_Num) | ||
126 | + { | ||
127 | + Num = s_Num; | ||
128 | + } | ||
129 | + /** | ||
130 | + * @brief Set Singer Name | ||
131 | + * @pre none. | ||
132 | + * @post Singer Name is set. | ||
133 | + * @param s_Singer Singer Name. | ||
134 | + */ | ||
135 | + void SetSinger(string s_Singer) | ||
136 | + { | ||
137 | + Singer = s_Singer; | ||
138 | + } | ||
139 | + | ||
140 | + /** | ||
141 | + * @brief Set Album Name | ||
142 | + * @pre none. | ||
143 | + * @post Album Name is set. | ||
144 | + * @param s_Album Album Name. | ||
145 | + */ | ||
146 | + void SetAlbum(string s_Album) | ||
147 | + { | ||
148 | + Album = s_Album; | ||
149 | + } | ||
150 | + /** | ||
151 | + * @brief Set Genre | ||
152 | + * @pre none. | ||
153 | + * @post Genre is set. | ||
154 | + * @param s_Genre Genre. | ||
155 | + */ | ||
156 | + void SetGenre(string s_Genre) | ||
157 | + { | ||
158 | + Genre = s_Genre; | ||
159 | + } | ||
160 | + /** | ||
161 | + * @brief Set Lyrics | ||
162 | + * @pre none. | ||
163 | + * @post Lyrics is set. | ||
164 | + * @param s_Lyrics Lyrics | ||
165 | + */ | ||
166 | + void SetLyrics(string s_Lyrics) | ||
167 | + { | ||
168 | + Lyrics = s_Lyrics; | ||
169 | + } | ||
170 | + /** | ||
171 | + * @brief Set Pkey | ||
172 | + * @pre none. | ||
173 | + * @post Pkey is set. | ||
174 | + */ | ||
175 | + void SetPkey() | ||
176 | + { | ||
177 | + Pkey = Name + Singer; | ||
178 | + } | ||
179 | + /** | ||
180 | + * @brief Set song information | ||
181 | + * @pre none. | ||
182 | + * @post song information is set | ||
183 | + * @param s_Name song Name | ||
184 | + * @param s_Singer Singer Name | ||
185 | + * @param s_Album Album Name. | ||
186 | + * @param s_Genre Genre | ||
187 | + * @param s_Lyrics Lyrics; | ||
188 | + */ | ||
189 | + void SetRecord(string s_Name, string s_Singer, string s_Album, string s_Genre, string s_Lyrics) | ||
190 | + { | ||
191 | + SetName(s_Name); | ||
192 | + SetSinger(s_Singer); | ||
193 | + SetAlbum(s_Album); | ||
194 | + SetGenre(s_Genre); | ||
195 | + SetLyrics(s_Lyrics); | ||
196 | + SetPkey(); | ||
197 | + } | ||
198 | + /** | ||
199 | + * @brief Display song Name on screen. | ||
200 | + * @pre song Name is set. | ||
201 | + * @post song Name is on screen. | ||
202 | + */ | ||
203 | + void DisplayNumOnScreen() | ||
204 | + { | ||
205 | + cout << "\tSong Number(Track Number) : " << Num << endl; | ||
206 | + }; | ||
207 | + /** | ||
208 | + * @brief Display song Name on screen. | ||
209 | + * @pre song Name is set. | ||
210 | + * @post song Name is on screen. | ||
211 | + */ | ||
212 | + void DisplayNameOnScreen() | ||
213 | + { | ||
214 | + cout << "\tSong Name : " << Name << endl; | ||
215 | + }; | ||
216 | + | ||
217 | + /** | ||
218 | + * @brief Display Singer Name on screen. | ||
219 | + * @pre Singer Name is set. | ||
220 | + * @post Singer Name is on screen. | ||
221 | + */ | ||
222 | + void DisplaySingerOnScreen() | ||
223 | + { | ||
224 | + cout << "\tSinger : " << Singer << endl; | ||
225 | + }; | ||
226 | + | ||
227 | + /** | ||
228 | + * @brief Display Album Name on screen. | ||
229 | + * @pre Album Name is set. | ||
230 | + * @post Album Name is on screen. | ||
231 | + */ | ||
232 | + void DisplayAlbumOnScreen() | ||
233 | + { | ||
234 | + cout << "\tAlbum : " << Album << endl; | ||
235 | + }; | ||
236 | + | ||
237 | + /** | ||
238 | + * @brief Display Genre on screen. | ||
239 | + * @pre Genre is set. | ||
240 | + * @post Genre is on screen. | ||
241 | + */ | ||
242 | + void DisplayGenreOnScreen() | ||
243 | + { | ||
244 | + cout << "\tGenre : " << Genre << endl; | ||
245 | + }; | ||
246 | + /** | ||
247 | +* @brief Display Lyrics on screen. | ||
248 | +* @pre Lyrics is set. | ||
249 | +* @post Lyrics is on screen. | ||
250 | +*/ | ||
251 | + void DisplayLyricsOnScreen() | ||
252 | + { | ||
253 | + cout << "\tLyrics : " << Lyrics << endl; | ||
254 | + }; | ||
255 | + /** | ||
256 | + * @brief Display an song information on screen. | ||
257 | + * @pre song information is set. | ||
258 | + * @post song information is on screen. | ||
259 | + */ | ||
260 | + void DisplayRecordOnScreen() | ||
261 | + { | ||
262 | + DisplayNumOnScreen(); | ||
263 | + DisplayNameOnScreen(); | ||
264 | + DisplaySingerOnScreen(); | ||
265 | + DisplayAlbumOnScreen(); | ||
266 | + DisplayGenreOnScreen(); | ||
267 | + DisplayLyricsOnScreen(); | ||
268 | + }; | ||
269 | + /** | ||
270 | + * @brief Set song Number from keyboard. | ||
271 | + * @pre none. | ||
272 | + * @post song Number is set. | ||
273 | + */ | ||
274 | + void SetNumFromKB(); | ||
275 | + /** | ||
276 | + * @brief Set song Name from keyboard. | ||
277 | + * @pre none. | ||
278 | + * @post song Name is set. | ||
279 | + */ | ||
280 | + void SetNameFromKB(); | ||
281 | + | ||
282 | + /** | ||
283 | + * @brief Set Singer Name from keyboard. | ||
284 | + * @pre none. | ||
285 | + * @post Singer Name is set. | ||
286 | + */ | ||
287 | + void SetSingerFromKB(); | ||
288 | + | ||
289 | + /** | ||
290 | + * @brief Set Album Name from keyboard. | ||
291 | + * @pre none. | ||
292 | + * @post Album Name is set. | ||
293 | + */ | ||
294 | + void SetAlbumFromKB(); | ||
295 | + /** | ||
296 | + * @brief Set Genre from keyboard. | ||
297 | + * @pre none. | ||
298 | + * @post Genre is set. | ||
299 | + */ | ||
300 | + void SetGenreFromKB(); | ||
301 | + /** | ||
302 | + * @brief Set Lyrics from keyboard. | ||
303 | + * @pre none. | ||
304 | + * @post Lyrics is set. | ||
305 | + */ | ||
306 | + void SetLyricsFromKB(); | ||
307 | + /** | ||
308 | + * @brief Set song information from keyboard. | ||
309 | + * @pre none. | ||
310 | + * @post song information is set. | ||
311 | + */ | ||
312 | + void SetInfoFromKB(); | ||
313 | + | ||
314 | + /** | ||
315 | + * @brief Read a record from file. | ||
316 | + * @pre the target file is opened. | ||
317 | + * @post student record is set. | ||
318 | + * @param fin file descriptor. | ||
319 | + * @return return 1 if this function works well, otherwise 0. | ||
320 | + */ | ||
321 | + int ReadDataFromFile(ifstream& fin); | ||
322 | + | ||
323 | + /** | ||
324 | + * @brief Write a record into file. | ||
325 | + * @pre the target file is opened. And the list should be initialized. | ||
326 | + * @post the target file is included the new student record. | ||
327 | + * @param fout file descriptor. | ||
328 | + * @return return 1 if this function works well, otherwise 0. | ||
329 | + */ | ||
330 | + int WriteDataToFile(ofstream& fout); | ||
331 | + | ||
332 | + /** | ||
333 | +* @brief 두 MusicType의 Primary key가 같은지 비교함 | ||
334 | +* @pre 비교하고자 하는 MusicType이 초기화 되어있어야함 | ||
335 | +* @post x | ||
336 | +* @param data 비교하고자 하는 데이터 | ||
337 | +* @return 같을경우 true, 다를경우 false | ||
338 | +*/ | ||
339 | + bool operator==(MusicType data) | ||
340 | + { | ||
341 | + | ||
342 | + if (this->GetPkey() == data.GetPkey()) | ||
343 | + return true; | ||
344 | + else | ||
345 | + return false; | ||
346 | + } | ||
347 | + /** | ||
348 | +* @brief 두 MusicType의 Primary key의 크기를 비교함 | ||
349 | +* @pre 비교하고자 하는 MusicType이 초기화 되어있어야함 | ||
350 | +* @post x | ||
351 | +* @param data 비교하고자 하는 데이터 | ||
352 | +* @return 좌변이 클경우 true 작을경우 false | ||
353 | + | ||
354 | +*/ | ||
355 | + bool operator>(MusicType data) | ||
356 | + { | ||
357 | + return (this->GetPkey() > data.GetPkey()); | ||
358 | + } | ||
359 | + /** | ||
360 | +* @brief 두 MusicType의 Primary key의 크기를 비교함 | ||
361 | +* @pre 비교하고자 하는 MusicType이 초기화 되어있어야함 | ||
362 | +* @post x | ||
363 | +* @param data 비교하고자 하는 데이터 | ||
364 | +* @return 우변이 클경우 true 작을경우 false | ||
365 | +*/ | ||
366 | + bool operator<(MusicType data) | ||
367 | + { | ||
368 | + return (this->GetPkey() < data.GetPkey()); | ||
369 | + | ||
370 | + } | ||
371 | + | ||
372 | + | ||
373 | +protected: | ||
374 | + int Num; //곡의 인덱스 | ||
375 | + string Name; //곡명 | ||
376 | + string Singer; //가수 | ||
377 | + string Album; //앨범 | ||
378 | + string Genre; //장르 | ||
379 | + string Lyrics; //가사 | ||
380 | + string Pkey; //Primary Key | ||
381 | +}; | ||
382 | + | ||
383 | + | ||
384 | + | ||
385 | + | ||
386 | +#endif // _MusicType_H |
Project/PLType.cpp
0 → 100644
1 | + | ||
2 | +#include "PLType.h" | ||
3 | + | ||
4 | +PLType::PLType(const PLType& data) | ||
5 | +{ | ||
6 | + PlayList = data.PlayList; | ||
7 | + PLname = data.PLname; | ||
8 | + length = data.length; | ||
9 | + | ||
10 | +} | ||
11 | +void PLType::Printall() | ||
12 | +{ | ||
13 | + DoublyIter2<ManageType*> Mgiter(PlayList); | ||
14 | + while (Mgiter.NotNull()) | ||
15 | + { | ||
16 | + cout << " : " << Mgiter.GetCurrentNode().data->getName() << endl; | ||
17 | + cout << "Index : " << Mgiter.GetCurrentNode().data->getIndex() << endl; | ||
18 | + Mgiter.Next(); | ||
19 | + } | ||
20 | + | ||
21 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/PLType.h
0 → 100644
1 | +#pragma once | ||
2 | +#include"ManageType.h" | ||
3 | +#include"UnSortedLinkedList.h" | ||
4 | +class PLType { | ||
5 | +private: | ||
6 | + | ||
7 | + UnSortedLinkedList<ManageType*> PlayList; | ||
8 | + string PLname; | ||
9 | + int length; | ||
10 | +public: | ||
11 | + PLType() { length = 0; PLname = ""; } | ||
12 | + ~PLType() {} | ||
13 | + PLType(const PLType& data); | ||
14 | + void setPLname(string N) | ||
15 | + { | ||
16 | + PLname = N; | ||
17 | + } | ||
18 | + string getPLname() | ||
19 | + { | ||
20 | + return PLname; | ||
21 | + } | ||
22 | + void AddListinList(ManageType* data) | ||
23 | + { | ||
24 | + PlayList.Add(data); | ||
25 | + length++; | ||
26 | + } | ||
27 | + void Printall(); | ||
28 | +}; |
Project/SortedLinkedList.h
0 → 100644
1 | +#pragma once | ||
2 | +#ifndef _DOUBLY_ITER_H | ||
3 | +#define _DOUBLY_ITER_H | ||
4 | +#include"DoublyIter.h" | ||
5 | + | ||
6 | +template <typename T> | ||
7 | +struct NodeType { | ||
8 | + T data; //각 노드의 데이터 | ||
9 | + NodeType* next;// 노드의 다음을 가리킬 포인터 | ||
10 | + NodeType* pre; | ||
11 | +}; | ||
12 | +template<typename T> | ||
13 | +class DoublyIter; | ||
14 | +/* | ||
15 | +* @bried 이 클래스는 더블소티드링크드리스트 | ||
16 | +*/ | ||
17 | +template<typename T> | ||
18 | +class SortedLinkedList | ||
19 | +{ | ||
20 | + friend class DoublyIter<T>; | ||
21 | +public: | ||
22 | + /** | ||
23 | +* default constructor. | ||
24 | +*/ | ||
25 | + SortedLinkedList(); | ||
26 | + | ||
27 | + /** | ||
28 | + * destructor. | ||
29 | + */ | ||
30 | + ~SortedLinkedList(); | ||
31 | + /** | ||
32 | + * @brief 깊은 복사를 위한 SortedLinkedList의 복사 연산자 | ||
33 | + * @pre anotherList가 초기화되어 있어야한다. | ||
34 | + * @post anotherList와 같은 정보를 가진 리스트가 생성된다 | ||
35 | + * @param anotherList 복사하고자 하는 SortedLinkedList | ||
36 | + */ | ||
37 | + SortedLinkedList(const SortedLinkedList<T>& anotherList); | ||
38 | + /** | ||
39 | + * @brief 링크드 리스트의 모든 노드를 제거한다. | ||
40 | + * @pre None. | ||
41 | + * @post 리스트가 비워진다. | ||
42 | + | ||
43 | + */ | ||
44 | + void MakeEmpty(); | ||
45 | + | ||
46 | + /** | ||
47 | + * @brief 리스트의 길이 = 원소의 개수 를 리턴함 | ||
48 | + * @pre x | ||
49 | + * @post 리턴값이 리스트의 길이가 된다 | ||
50 | + * @return 리스트의 길이 = 원소의 개수 | ||
51 | + */ | ||
52 | + int GetLength() | ||
53 | + { | ||
54 | + return m_nLength; | ||
55 | + } | ||
56 | + /** | ||
57 | + * @brief 새로운 노드의 값을 비교하여 맞는 위치에 추가한다 | ||
58 | + * @pre List is not Full(메모리에 빈 공간이 있어야 한다) | ||
59 | + * @post 리스트에 아이템이 추가된다. | ||
60 | + * @return 추가되면 1 아니면 0 | ||
61 | + * @param 추가하고자 하는 데이터값 | ||
62 | + */ | ||
63 | + int Add(T& data); | ||
64 | + /** | ||
65 | + * @brief 입력한 정보와 같은 정보를 가진 리스트의 원소를 리스트에서 삭제한다 | ||
66 | + * @pre 리스트가 비어있지 않아야한다. | ||
67 | + * @post 리스트의 원소가 삭제되고 길이가 짧아진다. | ||
68 | + * @return 삭제됬으면 1 아니면 0 | ||
69 | + * @param data 삭제하고자 하는 데이터값 | ||
70 | + */ | ||
71 | + int Delete(T& data); | ||
72 | + /** | ||
73 | + * @brief 리스트내의 정보를 바꾼다 | ||
74 | + * @pre 리스트에 하나이상의 원소가 있어야한다. | ||
75 | + * @post 리스트내의 원소의 정보가 바뀐다 | ||
76 | + * @return 작동했으면 1 아니면 0 | ||
77 | + */ | ||
78 | + int Replace(T& data); | ||
79 | + /** | ||
80 | + * @brief 리스트에서 Primarykey를 기준으로 일치하는 원소를 받아온다 | ||
81 | + * @pre 리스트내의 정보가 초기화되있어야 한다 | ||
82 | + * @post 키와 맞는 정보가 있으면 그것을 받아온다.. | ||
83 | + * @return 찾아왔으면 1, 못찾았으면 0 | ||
84 | + */ | ||
85 | + int Get(T& item); | ||
86 | + /** | ||
87 | + * @brief 리스트가 비어있는지를 확인한다. | ||
88 | + * @pre x | ||
89 | + * @post x | ||
90 | + * @return 비었으면 1, 아니면 0 | ||
91 | + */ | ||
92 | + bool IsEmpty() | ||
93 | + { | ||
94 | + if (m_nLength == 0) | ||
95 | + return true; | ||
96 | + else | ||
97 | + return false; | ||
98 | + } | ||
99 | + | ||
100 | + /** | ||
101 | + * @brief 복사 생성자를 이용한 대입 연산자 | ||
102 | + * @pre anotherList가 정의되어 있어야한다. | ||
103 | + * @post 깊은 복사된 리스트가 대입된다. | ||
104 | + * @return 복사된 리스트 | ||
105 | + */ | ||
106 | + SortedLinkedList<T> operator=(const SortedLinkedList<T> &anotherList); | ||
107 | + | ||
108 | +private: | ||
109 | + NodeType<T> *m_pList; | ||
110 | + NodeType<T> *m_pLast; | ||
111 | + int m_nLength; | ||
112 | +}; | ||
113 | + | ||
114 | + | ||
115 | + | ||
116 | +//함수 정의부 | ||
117 | +template<typename T> | ||
118 | +SortedLinkedList<T>::SortedLinkedList() | ||
119 | +{ | ||
120 | + m_nLength = 0; | ||
121 | + m_pList = NULL; | ||
122 | + | ||
123 | + | ||
124 | +} | ||
125 | +template<typename T> | ||
126 | +SortedLinkedList<T>::~SortedLinkedList() | ||
127 | +{ | ||
128 | + MakeEmpty();//메모리누수를 막기위해 노드의 데이터를 모두 제거한다 | ||
129 | + | ||
130 | +} | ||
131 | +template<typename T> | ||
132 | +void SortedLinkedList<T>::MakeEmpty() | ||
133 | +{ | ||
134 | + NodeType<T> *tempptr; | ||
135 | + DoublyIter<T> iter(*this); | ||
136 | + while (iter.NotNull()) | ||
137 | + { | ||
138 | + tempptr = iter.CurPointer; | ||
139 | + iter.Next(); | ||
140 | + delete tempptr; | ||
141 | + } //리스트내의 모든 노드를 제거 | ||
142 | + | ||
143 | + m_pList = NULL; | ||
144 | + m_pLast = NULL; | ||
145 | + m_nLength = 0; | ||
146 | + | ||
147 | +} | ||
148 | + | ||
149 | +template<typename T> | ||
150 | +int SortedLinkedList<T>::Add(T &data) | ||
151 | +{ | ||
152 | + | ||
153 | + | ||
154 | + | ||
155 | + NodeType<T> *Node = new NodeType<T>; | ||
156 | + NodeType<T> *Pre; | ||
157 | + DoublyIter<T> iter(*this); | ||
158 | + bool Found = false; | ||
159 | + T dummy; | ||
160 | + | ||
161 | + | ||
162 | + Node->data = data; | ||
163 | + Node->next = NULL; | ||
164 | + Node->pre = NULL; | ||
165 | + if (IsEmpty()) //비어있을 경우 | ||
166 | + { | ||
167 | + m_pList = Node; | ||
168 | + m_pLast = m_pList; | ||
169 | + m_nLength++; //성공적으로 추가했으므로 길이를 늘려준다 | ||
170 | + } | ||
171 | + //list에 노드가 있을경우 | ||
172 | + else | ||
173 | + { | ||
174 | + while (1) | ||
175 | + { | ||
176 | + | ||
177 | + //Pre = m_pCurPointer; //이전 노드를 가리키는 포인터 갱신, 첫 시작은 m_pList로 리스트의 첫부분이다 | ||
178 | + | ||
179 | + | ||
180 | + if (iter.CurPointer->data == Node->data) | ||
181 | + break; //같은 데이터가 있을경우 추가하지 않고 반복문을 탈출한다.. | ||
182 | + | ||
183 | + if (iter.CurPointer->data > Node->data) //Node의 데이터가 현재 포인터의 값보다 작아질때까지 node가 들어갈 위치를 뒤로 민다. | ||
184 | + { | ||
185 | + if (iter.CurPointer->pre == NULL) //리스트 맨 앞 장소에 넣어야 할때 첫번째 원소로 삽입한다 | ||
186 | + { | ||
187 | + | ||
188 | + Node->next = iter.CurPointer; | ||
189 | + iter.CurPointer->pre = Node; | ||
190 | + m_pList = Node; | ||
191 | + m_nLength++; //성공적으로 추가했으므로 break 하기전에 길이를 늘려준다 | ||
192 | + | ||
193 | + break; | ||
194 | + } | ||
195 | + Node->next = iter.CurPointer; | ||
196 | + Node->pre = iter.CurPointer->pre; | ||
197 | + iter.CurPointer->pre->next = Node; | ||
198 | + iter.CurPointer->pre = Node; | ||
199 | + m_nLength++; //성공적으로 추가했으므로 break 하기전 길이를 늘려준다. | ||
200 | + break; | ||
201 | + | ||
202 | + | ||
203 | + } | ||
204 | + | ||
205 | + //Node 포인터가 마지막 노드를 가리키면 그 뒤에 Node를 삽입한다. | ||
206 | + if (iter.CurPointer->next == NULL) | ||
207 | + { | ||
208 | + Node->pre = iter.CurPointer; | ||
209 | + iter.CurPointer->next = Node; | ||
210 | + | ||
211 | + m_pLast = Node; | ||
212 | + m_nLength++; | ||
213 | + break; | ||
214 | + | ||
215 | + } | ||
216 | + iter.Next(); | ||
217 | + | ||
218 | + | ||
219 | + } | ||
220 | + | ||
221 | + | ||
222 | + | ||
223 | + | ||
224 | + } | ||
225 | + | ||
226 | + | ||
227 | + return 1; | ||
228 | +} | ||
229 | + | ||
230 | +template<typename T> | ||
231 | +int SortedLinkedList<T>::Delete(T& data) | ||
232 | +{ | ||
233 | + bool MoreToSearch, found; | ||
234 | + NodeType<T> *Pre = NULL; | ||
235 | + DoublyIter<T> iter(*this); | ||
236 | + | ||
237 | + found = false; | ||
238 | + MoreToSearch = iter.NotNull(); | ||
239 | + | ||
240 | + while (MoreToSearch && !found) | ||
241 | + { | ||
242 | + if (data == iter.CurPointer->data) //현재 가리키는 원소가 패러미터로 넣은 값과 같은가? | ||
243 | + { | ||
244 | + found = true; //찾았으므로 found = true | ||
245 | + if (Pre == NULL) //찾은 항목이 첫번째 원소일경우 | ||
246 | + { | ||
247 | + NodeType<T>* temp = iter.CurPointer; //첫번째 원소의 다음원소를 저장할 임시 포인터선언 | ||
248 | + delete m_pList; //첫원소를 삭제한다. | ||
249 | + temp->pre = NULL; | ||
250 | + m_pList = temp; //찾은 항목이 첫 항목일경우 다음 원소를 첫번째 원소로 한다. | ||
251 | + | ||
252 | + } | ||
253 | + else | ||
254 | + { | ||
255 | + | ||
256 | + Pre->next = iter.CurPointer->next; | ||
257 | + iter.CurPointer->next->pre = Pre; | ||
258 | + delete iter.CurPointer; | ||
259 | + } | ||
260 | + | ||
261 | + | ||
262 | + | ||
263 | + } | ||
264 | + else | ||
265 | + { | ||
266 | + Pre = iter.CurPointer; | ||
267 | + iter.Next(); | ||
268 | + MoreToSearch = (iter.NotNull()); | ||
269 | + | ||
270 | + } //못 찾을경우 m_CurPointer은 다음 원소를 가리킨다. 단 Pre는 현재원소를 가리킨다. | ||
271 | + } | ||
272 | + | ||
273 | + if (found) //찾았을 경우 | ||
274 | + { | ||
275 | + m_nLength--; | ||
276 | + return 1; | ||
277 | + | ||
278 | + } | ||
279 | + else //못 찾으면 | ||
280 | + return 0; | ||
281 | + | ||
282 | + | ||
283 | + | ||
284 | +} | ||
285 | + | ||
286 | +template<typename T> | ||
287 | +int SortedLinkedList<T>::Replace(T& data) | ||
288 | +{ | ||
289 | + bool MoreToSearch, found; | ||
290 | + NodeType<T> *location; | ||
291 | + | ||
292 | + location = m_pList; | ||
293 | + found = false; | ||
294 | + MoreToSearch = (location != NULL); | ||
295 | + | ||
296 | + while (MoreToSearch && !found) //리스트의 끝이 아니면서 아직 몾찾을경우 반복한다 | ||
297 | + { | ||
298 | + if (data == location->data) //일치하는 경우를 찾으면 | ||
299 | + { | ||
300 | + found = true; | ||
301 | + location->data = data; | ||
302 | + } //찾았으므로 found 는 true가되고 해당위치에 data값을 넣는다 | ||
303 | + else | ||
304 | + { | ||
305 | + location = location->next; | ||
306 | + MoreToSearch = (location != NULL); //리스트의 끝이 아닐경우 계속찾는다. | ||
307 | + | ||
308 | + } //찾지 못했을 때 다음 location으로 옮긴다. | ||
309 | + | ||
310 | + } | ||
311 | + | ||
312 | + if (found) //찾았을 경우 | ||
313 | + { | ||
314 | + return 1; | ||
315 | + | ||
316 | + } | ||
317 | + else | ||
318 | + return 0; //못 찾음 | ||
319 | + | ||
320 | +} | ||
321 | + | ||
322 | +template<typename T> | ||
323 | +int SortedLinkedList<T>::Get(T& data) | ||
324 | +{ | ||
325 | + bool MoreToSearch, found; | ||
326 | + NodeType<T>* location; | ||
327 | + | ||
328 | + location = m_pList; | ||
329 | + found = false; | ||
330 | + MoreToSearch = (location != NULL); | ||
331 | + | ||
332 | + while (MoreToSearch && !found) | ||
333 | + { | ||
334 | + if (data == location->data) //일치하는 항목을 찾으면 | ||
335 | + { | ||
336 | + found = true; | ||
337 | + data = location->data; | ||
338 | + } | ||
339 | + else | ||
340 | + { | ||
341 | + | ||
342 | + location = location->next; //못찾으면 다음위치로 민다 | ||
343 | + MoreToSearch = (location != NULL); //다음위치가 마지막이 아닐경우 계속 찾는다. | ||
344 | + } | ||
345 | + | ||
346 | + } | ||
347 | + if (found) //찾았으면 | ||
348 | + return 1; | ||
349 | + else //못 찾았으면 | ||
350 | + { | ||
351 | + return 0; | ||
352 | + } | ||
353 | + | ||
354 | + | ||
355 | + | ||
356 | +} | ||
357 | + | ||
358 | + | ||
359 | + | ||
360 | + | ||
361 | + | ||
362 | + | ||
363 | + | ||
364 | + | ||
365 | + | ||
366 | + | ||
367 | +template<typename T> | ||
368 | +SortedLinkedList<T>::SortedLinkedList(const SortedLinkedList<T>& anotherList) | ||
369 | +{ | ||
370 | + NodeType<T> *m_pCurPointer; | ||
371 | + m_pList = NULL; | ||
372 | + m_pCurPointer = NULL; | ||
373 | + if (anotherList.m_pList == NULL) | ||
374 | + return; | ||
375 | + else { | ||
376 | + this->m_nLength = anotherList.m_nLength; | ||
377 | + | ||
378 | + NodeType<T> *Node1 = new NodeType<T>; | ||
379 | + NodeType<T> *preNode; | ||
380 | + NodeType<T> *Node2; | ||
381 | + m_pList = Node1; | ||
382 | + Node1->data = anotherList.m_pList->data; | ||
383 | + Node1->pre = NULL; | ||
384 | + Node2 = anotherList.m_pList->next; | ||
385 | + | ||
386 | + while (Node2 != NULL) | ||
387 | + { | ||
388 | + Node1->next = new NodeType<T>; | ||
389 | + preNode = Node1; | ||
390 | + Node1 = Node1->next; | ||
391 | + Node1->data = Node2->data; | ||
392 | + Node1->pre = preNode; | ||
393 | + Node2 = Node2->next; | ||
394 | + | ||
395 | + | ||
396 | + } | ||
397 | + Node1->next = NULL; | ||
398 | + | ||
399 | + } | ||
400 | + | ||
401 | + | ||
402 | +} | ||
403 | + | ||
404 | +template<typename T> | ||
405 | +SortedLinkedList<T> SortedLinkedList<T>::operator=(const SortedLinkedList<T> &anotherList) | ||
406 | +{ | ||
407 | + MakeEmpty(); | ||
408 | + SortedLinkedList<T> temp(anotherList); | ||
409 | + | ||
410 | + return temp; | ||
411 | + | ||
412 | +} | ||
413 | + | ||
414 | + | ||
415 | +#endif // !_SORTED_LINKED_LIST_H | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/UnSortedLinkedList.h
0 → 100644
1 | +#pragma once | ||
2 | +#ifndef _DOUBLY_ITER2_H | ||
3 | +#define _DOUBLY_ITER2_H | ||
4 | +#include"DoublyIter2.h" | ||
5 | + | ||
6 | +template <typename T> | ||
7 | +struct NodeType2 { | ||
8 | + T data; //각 노드의 데이터 | ||
9 | + NodeType2* next;// 노드의 다음을 가리킬 포인터 | ||
10 | + NodeType2* pre; | ||
11 | +}; | ||
12 | +template<typename T> | ||
13 | +class DoublyIter2; | ||
14 | +/* | ||
15 | +* @bried 이 클래스는 더블소티드링크드리스트 | ||
16 | +*/ | ||
17 | +template<typename T> | ||
18 | +class UnSortedLinkedList | ||
19 | +{ | ||
20 | + friend class DoublyIter2<T>; | ||
21 | +public: | ||
22 | + /** | ||
23 | +* default constructor. | ||
24 | +*/ | ||
25 | + UnSortedLinkedList(); | ||
26 | + | ||
27 | + /** | ||
28 | + * destructor. | ||
29 | + */ | ||
30 | + ~UnSortedLinkedList(); | ||
31 | + /** | ||
32 | + * @brief 깊은 복사를 위한 UnSortedLinkedList의 복사 연산자 | ||
33 | + * @pre anotherList가 초기화되어 있어야한다. | ||
34 | + * @post anotherList와 같은 정보를 가진 리스트가 생성된다 | ||
35 | + * @param anotherList 복사하고자 하는 UnSortedLinkedList | ||
36 | + */ | ||
37 | + UnSortedLinkedList(const UnSortedLinkedList<T>& anotherList); | ||
38 | + /** | ||
39 | + * @brief 링크드 리스트의 모든 노드를 제거한다. | ||
40 | + * @pre None. | ||
41 | + * @post 리스트가 비워진다. | ||
42 | + | ||
43 | + */ | ||
44 | + void MakeEmpty(); | ||
45 | + | ||
46 | + /** | ||
47 | + * @brief 리스트의 길이 = 원소의 개수 를 리턴함 | ||
48 | + * @pre x | ||
49 | + * @post 리턴값이 리스트의 길이가 된다 | ||
50 | + * @return 리스트의 길이 = 원소의 개수 | ||
51 | + */ | ||
52 | + int GetLength() | ||
53 | + { | ||
54 | + return m_nLength; | ||
55 | + } | ||
56 | + /** | ||
57 | + * @brief 새로운 노드의 값을 비교하여 맞는 위치에 추가한다 | ||
58 | + * @pre List is not Full(메모리에 빈 공간이 있어야 한다) | ||
59 | + * @post 리스트에 아이템이 추가된다. | ||
60 | + * @return 추가되면 1 아니면 0 | ||
61 | + * @param 추가하고자 하는 데이터값 | ||
62 | + */ | ||
63 | + int Add(T& data); | ||
64 | + /** | ||
65 | + * @brief 입력한 정보와 같은 정보를 가진 리스트의 원소를 리스트에서 삭제한다 | ||
66 | + * @pre 리스트가 비어있지 않아야한다. | ||
67 | + * @post 리스트의 원소가 삭제되고 길이가 짧아진다. | ||
68 | + * @return 삭제瑛만 1 아니면 0 | ||
69 | + * @param data 삭제하고자 하는 데이터값 | ||
70 | + */ | ||
71 | + int Delete(T& data); | ||
72 | + /** | ||
73 | + * @brief 리스트내의 정보를 바꾼다 | ||
74 | + * @pre 리스트에 하나이상의 원소가 있어야한다. | ||
75 | + * @post 리스트내의 원소의 정보가 바뀐다 | ||
76 | + * @return 작동했으면 1 아니면 0 | ||
77 | + */ | ||
78 | + int Replace(T& data); | ||
79 | + /** | ||
80 | + * @brief 리스트에서 Primarykey를 기준으로 일치하는 원소를 받아온다 | ||
81 | + * @pre 리스트내의 정보가 초기화되있어야 한다 | ||
82 | + * @post 키와 맞는 정보가 있으면 그것을 받아온다.. | ||
83 | + * @return 찾아왔으면 1, 못찾았으면 0 | ||
84 | + */ | ||
85 | + int Get(T& item); | ||
86 | + /** | ||
87 | + * @brief 리스트가 비어있는지를 확인한다. | ||
88 | + * @pre x | ||
89 | + * @post x | ||
90 | + * @return 비었으면 1, 아니면 0 | ||
91 | + */ | ||
92 | + bool IsEmpty() const | ||
93 | + { | ||
94 | + if (m_nLength == 0) | ||
95 | + return true; | ||
96 | + else | ||
97 | + return false; | ||
98 | + } | ||
99 | + | ||
100 | + /** | ||
101 | + * @brief 복사 생성자를 이용한 대입 연산자 | ||
102 | + * @pre anotherList가 정의되어 있어야한다. | ||
103 | + * @post 깊은 복사된 리스트가 대입된다. | ||
104 | + * @return 복사된 리스트 | ||
105 | + */ | ||
106 | + UnSortedLinkedList<T> operator=(const UnSortedLinkedList<T> &anotherList); | ||
107 | + | ||
108 | +private: | ||
109 | + NodeType2<T> *m_pList; | ||
110 | + NodeType2<T> *m_pLast; | ||
111 | + int m_nLength; | ||
112 | +}; | ||
113 | + | ||
114 | + | ||
115 | + | ||
116 | +//함수 정의부 | ||
117 | +template<typename T> | ||
118 | +UnSortedLinkedList<T>::UnSortedLinkedList() | ||
119 | +{ | ||
120 | + m_nLength = 0; | ||
121 | + m_pList = NULL; | ||
122 | + | ||
123 | + | ||
124 | +} | ||
125 | +template<typename T> | ||
126 | +UnSortedLinkedList<T>::~UnSortedLinkedList() | ||
127 | +{ | ||
128 | + MakeEmpty();//메모리누수를 막기위해 노드의 데이터를 모두 제거한다 | ||
129 | + | ||
130 | +} | ||
131 | +template<typename T> | ||
132 | +void UnSortedLinkedList<T>::MakeEmpty() | ||
133 | +{ | ||
134 | + NodeType2<T> *tempptr; | ||
135 | + DoublyIter2<T> iter(*this); | ||
136 | + while (iter.NotNull()) | ||
137 | + { | ||
138 | + tempptr = iter.CurPointer; | ||
139 | + iter.Next(); | ||
140 | + delete tempptr; | ||
141 | + } //리스트내의 모든 노드를 제거 | ||
142 | + m_pList = NULL; | ||
143 | + m_pLast = NULL; | ||
144 | + m_nLength = 0; | ||
145 | +} | ||
146 | + | ||
147 | +template<typename T> | ||
148 | +int UnSortedLinkedList<T>::Add(T &data) | ||
149 | +{ | ||
150 | + | ||
151 | + | ||
152 | + | ||
153 | + NodeType2<T> *Node = new NodeType2<T>; | ||
154 | + NodeType2<T> *Pre; | ||
155 | + DoublyIter2<T> iter(*this); | ||
156 | + bool Found = false; | ||
157 | + T dummy; | ||
158 | + | ||
159 | + | ||
160 | + Node->data = data; | ||
161 | + Node->next = NULL; | ||
162 | + Node->pre = NULL; | ||
163 | + if (IsEmpty()) //비어있을 경우 | ||
164 | + { | ||
165 | + m_pList = Node; | ||
166 | + m_pLast = m_pList; | ||
167 | + m_nLength++; //성공적으로 추가했으므로 길이를 늘려준다 | ||
168 | + } | ||
169 | + //list에 노드가 있을경우 | ||
170 | + else | ||
171 | + { | ||
172 | + while (1) | ||
173 | + { | ||
174 | + | ||
175 | + //Pre = m_pCurPointer; //이전 노드를 가리키는 포인터 갱신, 첫 시작은 m_pList로 리스트의 첫부분이다 | ||
176 | + Pre = iter.CurPointer; | ||
177 | + | ||
178 | + | ||
179 | + | ||
180 | + //Node 포인터가 마지막 노드를 가리키면 그 뒤에 Node를 삽입한다. | ||
181 | + if (iter.CurPointer->next == NULL) | ||
182 | + { | ||
183 | + iter.CurPointer->next = Node; | ||
184 | + Node->pre = iter.CurPointer; | ||
185 | + m_pLast = Node; | ||
186 | + m_nLength++; | ||
187 | + break; | ||
188 | + | ||
189 | + } | ||
190 | + iter.Next(); | ||
191 | + | ||
192 | + | ||
193 | + } | ||
194 | + | ||
195 | + | ||
196 | + | ||
197 | + | ||
198 | + } | ||
199 | + | ||
200 | + | ||
201 | + return 1; | ||
202 | +} | ||
203 | + | ||
204 | +template<typename T> | ||
205 | +int UnSortedLinkedList<T>::Delete(T& data) | ||
206 | +{ | ||
207 | + bool MoreToSearch, found; | ||
208 | + NodeType2<T> *Pre = NULL; | ||
209 | + DoublyIter2<T> iter(*this); | ||
210 | + | ||
211 | + found = false; | ||
212 | + MoreToSearch = iter.NotNull(); | ||
213 | + | ||
214 | + while (MoreToSearch && !found) | ||
215 | + { | ||
216 | + if (data == iter.CurPointer->data) //현재 가리키는 원소가 패러미터로 넣은 값과 같은가? | ||
217 | + { | ||
218 | + found = true; //찾았으므로 found = true | ||
219 | + if (Pre == NULL) //찾은 항목이 첫번째 원소일경우 | ||
220 | + { | ||
221 | + NodeType2<T>* temp = iter.CurPointer; //첫번째 원소의 다음원소를 저장할 임시 포인터선언 | ||
222 | + delete m_pList; //첫원소를 삭제한다. | ||
223 | + temp->pre = NULL; | ||
224 | + m_pList = temp; //찾은 항목이 첫 항목일경우 다음 원소를 첫번째 원소로 한다. | ||
225 | + | ||
226 | + } | ||
227 | + else | ||
228 | + { | ||
229 | + | ||
230 | + Pre->next = iter.CurPointer->next; | ||
231 | + iter.CurPointer->next->pre = Pre; | ||
232 | + delete iter.CurPointer; | ||
233 | + } | ||
234 | + | ||
235 | + | ||
236 | + | ||
237 | + } | ||
238 | + else | ||
239 | + { | ||
240 | + Pre = iter.CurPointer; | ||
241 | + iter.Next(); | ||
242 | + MoreToSearch = (iter.NotNull()); | ||
243 | + | ||
244 | + } //못 찾을경우 m_CurPointer은 다음 원소를 가리킨다. 단 Pre는 현재원소를 가리킨다. | ||
245 | + } | ||
246 | + | ||
247 | + if (found) //찾았을 경우 | ||
248 | + { | ||
249 | + m_nLength--; | ||
250 | + return 1; | ||
251 | + | ||
252 | + } | ||
253 | + else //못 찾으면 | ||
254 | + return 0; | ||
255 | + | ||
256 | + | ||
257 | + | ||
258 | +} | ||
259 | + | ||
260 | +template<typename T> | ||
261 | +int UnSortedLinkedList<T>::Replace(T& data) | ||
262 | +{ | ||
263 | + bool MoreToSearch, found; | ||
264 | + NodeType2<T> *location; | ||
265 | + | ||
266 | + location = m_pList; | ||
267 | + found = false; | ||
268 | + MoreToSearch = (location != NULL); | ||
269 | + | ||
270 | + while (MoreToSearch && !found) //리스트의 끝이 아니면서 아직 ▣@뺐嚥 반복한다 | ||
271 | + { | ||
272 | + if (data == location->data) //일치하는 경우를 찾으면 | ||
273 | + { | ||
274 | + found = true; | ||
275 | + location->data = data; | ||
276 | + } //찾았으므로 found 는 true가되고 해당위치에 data값을 넣는다 | ||
277 | + else | ||
278 | + { | ||
279 | + location = location->next; | ||
280 | + MoreToSearch = (location != NULL); //리스트의 끝이 아닐경우 계속찾는다. | ||
281 | + | ||
282 | + } //찾지 못했을 때 다음 location으로 옮긴다. | ||
283 | + | ||
284 | + } | ||
285 | + | ||
286 | + if (found) //찾았을 경우 | ||
287 | + { | ||
288 | + return 1; | ||
289 | + | ||
290 | + } | ||
291 | + else | ||
292 | + return 0; //못 찾음 | ||
293 | + | ||
294 | +} | ||
295 | + | ||
296 | +template<typename T> | ||
297 | +int UnSortedLinkedList<T>::Get(T& data) | ||
298 | +{ | ||
299 | + bool MoreToSearch, found; | ||
300 | + NodeType2<T>* location; | ||
301 | + | ||
302 | + location = m_pList; | ||
303 | + found = false; | ||
304 | + MoreToSearch = (location != NULL); | ||
305 | + | ||
306 | + while (MoreToSearch && !found) | ||
307 | + { | ||
308 | + if (data == location->data) //일치하는 항목을 찾으면 | ||
309 | + { | ||
310 | + found = true; | ||
311 | + data = location->data; | ||
312 | + } | ||
313 | + else | ||
314 | + { | ||
315 | + | ||
316 | + location = location->next; //못찾으면 다음위치로 민다 | ||
317 | + MoreToSearch = (location != NULL); //다음위치가 마지막이 아닐경우 계속 찾는다. | ||
318 | + } | ||
319 | + | ||
320 | + } | ||
321 | + if (found) //찾았으면 | ||
322 | + return 1; | ||
323 | + else //못 찾았으면 | ||
324 | + { | ||
325 | + return 0; | ||
326 | + } | ||
327 | + | ||
328 | + | ||
329 | + | ||
330 | +} | ||
331 | + | ||
332 | + | ||
333 | + | ||
334 | + | ||
335 | + | ||
336 | + | ||
337 | + | ||
338 | + | ||
339 | + | ||
340 | + | ||
341 | +template<typename T> | ||
342 | +UnSortedLinkedList<T>::UnSortedLinkedList(const UnSortedLinkedList<T>& anotherList) | ||
343 | +{ | ||
344 | + NodeType2<T> *m_pCurPointer; | ||
345 | + m_pList = NULL; | ||
346 | + m_pCurPointer = NULL; | ||
347 | + if (anotherList.m_pList == NULL) | ||
348 | + return; | ||
349 | + else { | ||
350 | + this->m_nLength = anotherList.m_nLength; | ||
351 | + | ||
352 | + NodeType2<T> *Node1 = new NodeType2<T>; | ||
353 | + NodeType2<T> *preNode; | ||
354 | + NodeType2<T> *Node2; | ||
355 | + m_pList = Node1; | ||
356 | + Node1->data = anotherList.m_pList->data; | ||
357 | + Node1->pre = NULL; | ||
358 | + Node2 = anotherList.m_pList->next; | ||
359 | + | ||
360 | + while (Node2 != NULL) | ||
361 | + { | ||
362 | + Node1->next = new NodeType2<T>; | ||
363 | + preNode = Node1; | ||
364 | + Node1 = Node1->next; | ||
365 | + Node1->data = Node2->data; | ||
366 | + Node1->pre = preNode; | ||
367 | + Node2 = Node2->next; | ||
368 | + | ||
369 | + | ||
370 | + } | ||
371 | + Node1->next = NULL; | ||
372 | + | ||
373 | + } | ||
374 | + | ||
375 | + | ||
376 | +} | ||
377 | + | ||
378 | +template<typename T> | ||
379 | +UnSortedLinkedList<T> UnSortedLinkedList<T>::operator=(const UnSortedLinkedList<T> &anotherList) | ||
380 | +{ | ||
381 | + MakeEmpty(); | ||
382 | + UnSortedLinkedList<T> temp(anotherList); | ||
383 | + | ||
384 | + return temp; | ||
385 | + | ||
386 | +} | ||
387 | + | ||
388 | + | ||
389 | +#endif // !_SORTED_LINKED_LIST_H | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
Project/main.cpp
0 → 100644
1 | +/** | ||
2 | +* @mainpage Array list. | ||
3 | +* This is a simple example of Lab01 on data structures course.<br> | ||
4 | +* | ||
5 | +* - Doxygen GUI 설정법<br> | ||
6 | +* Step 1: Doxygen 으로 문서화 할 프로젝트 경로 삽입.<br> | ||
7 | +* Step 2: Wizard 탭에서 Project Name 설정.<br> | ||
8 | +* Step 3: Wizard 탭에서 Source code directory 에 문서화 할 소스 경로 지정 후 Scan recursively 를 체크. | ||
9 | +* [Step 1] 의 경로와 같은 경로를 삽입해도 됨.<br> | ||
10 | +* Step 4: Destination directory 에 문서화한 데이터가 저장될 경로 지정.<br> | ||
11 | +* Step 5: Wizard 탭의 Output 에서 LaTeX 체크 해제.<br> | ||
12 | +* Step 6: Run 탭의 Run doxygen 수행 후, "Doxygen has finished" 확인.<br> | ||
13 | +* | ||
14 | +* - 한글사용을 위해서는 Doxywizard에서 아래와 같이 설정할 것.<br> | ||
15 | +* Expert 탭 -> Input (Topics 에서 선택) -> INPUT_ENCODING 을 "EUC-KR" 로 설정. | ||
16 | +* | ||
17 | +* @date 2018-10-11 | ||
18 | +* @author 2016104132 안형준 | ||
19 | +*/ | ||
20 | + | ||
21 | +#include "Application.h" | ||
22 | + | ||
23 | +/** | ||
24 | +* program main function for data structures course. | ||
25 | +*/ | ||
26 | +int main() | ||
27 | +{ | ||
28 | + Application app; // Program application | ||
29 | + app.Run(); // run program | ||
30 | + | ||
31 | + return 0; | ||
32 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
-
Please register or login to post a comment