# Допълнително упражнение 2 - УПП, 04.12.2023 \n GitHub classroom: [url https://classroom.github.com/a/CrerXpf6 classroom.github.com/a/CrerXpf6] .important Следете внимателно дали триете всичката си динамична памет коректно на всяка подточка! Случвало се е на контролни да се пишат двойки ако всичко друго е коректно, но има неизтрита памет! ## Задача - текстов редактор Ще направим един прост текстов редактор. От входа ще получавате редове текст, в общия случай редовете ще бъдат някакво текстово съдъражение, което ще трябва да запазите в паметта. Определени редове ще имат команди, чрез които ще *[редактирате]* вече въведения текст. Задачата е сравнително голяма, затова е разделена на подточки, като всяка надгражда предходната. ### а) въвеждане на текст без команди Като за начало, нека да имплементираме запазването на текст. От конзолата ще получавате редове текст, всеки ред ще е с максимална дължина от 1024 знака, след това трябва да го запазите. .important Може да използвате масив със статична дължина за буфер, обаче трябва да използвате възможно най-малко памет за "перманентното" запазване на реда текст във вашата програма. Използвайте многомерен масив за запазване на редовете, вместо всичко да се запазва в един голям низ. Това е нужно за бъдещи подточки. *[Само за тестване]*, набързо имплементирайте проверка, ако първата буква от реда е `[Q]`, тогава програмата да спре да приема вход, да изкара въведения текст до сега и да приключи. =[Пример:]= *[Смесен вход/изход]* ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. ### б) функция за извеждане на команди Команда е един ред текст, като първата буква, различна от шпация, е `[:]`. След нея има нула или повече шпации и още една буква, тази буква определя коя команда искаме да използваме. В зависимост от командата, може да имаме параметри, поставени след буквата за командата. Параметрите не съдържат шпации и параметрите са разделени помежду си с поне една шпация. Тоест, един команден ред ще бъде в този формат (като нещата в квадратните скоби са описания, какво има на конкретното място): [≥0 шпации]:[≥0 шпации][буква][≥0 шпации][параметър 1][≥1 шпации][параметър 2]...[≥1 шпации][последен параметър] Командите не се запазват като част от текста. Имплементирайте функция `[extractCommand]`, която приема низ. Ако низът е команда, тогава връща масив от низове, първия от които съдържа буквата, определяща командата, докато останалите низове са параметрите. Ако низът не е команда, тогава връща празен масив. .warn Какво означава празен масив зависи от имплементацията ви. За предпочитане е да не заделяте памет, когато не е нужно. .question Как ще върнем масив? Нужно ли е да връщаме бройката елементи? *[Само за тестване]*, след всеки въведен ред, ако е команда, изкарайте извлечените стойности от `[extractCommand]`, със запетайки след всяка. Като при [url #section подточка a)], ако редът започва с `[Q]`, спирате приемане на вход и изкарвате запазения текст. =[Пример:]= *[Смесен вход/изход]* ```terminal DAY HAD DAWNED COLD AND GRAY WHEN :A bcd 012 345 A,bcd,012,345, the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- :A A, : A A, : A abc A,abc, est. It was a high bank, and he paused to breathe at the top. : A123 456 789 A B C A,123,456,789,A,B,C, Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. ### в) команда print Имплементирайте функция `[print]`, която приема масив, съдържащ целия запазен текст, и го изкарва на екрана, като преди всеки ред изкарва неговия номер (първи ред има номер 1, втори има номер 2, так. нат.) с =[вмъкнати водещи нули]= (така че всяко число да бъде съставено от един и същ брой знаци). Ако текстът е празен, не изкарва нищо. Тоест, ако сме въвели текст от 7 реда, `[print]` ще изкара: ```terminal 1 First line 2 Second line ... 7 Last line Ако сме въвели 23 реда: ```terminal 01 First line 02 Second line ... 09 Ninth line 10 Tenth line 11 Eleventh line ... 23 Last line Ако сме въвели 130 реда: ```terminal 001 First line ... 009 Ninth line 010 Tenth line ... 099 99th line 100 100th line ... 130 Last line Командата, която използва тази функция, се определя с главната буква `[P]` и няма параметри. За всички команди (за момента само `[P]`): .bulleted - Обновете програмата, така че при валидна команда, да изпълни съответната и функция и да продължи изпълнение. - Ако срещнете недефинирана команда, трябва да изкарате на екрана "; Not an editor command" и изпълнението на програмата да продължи. - Ако срещнете допълнителни/излишни параметри, трябва да изкарате "; Excess parameters", но функцията да се изпълни с коректния брой параметри. =[Пример:]= *[Смесен вход/изход]* ```terminal DAY HAD DAWNED COLD AND GRAY WHEN :P 1 DAY HAD DAWNED COLD AND GRAY WHEN :M ; Not an editor command the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- :P A 7 n ; Excess parameters 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. ### г) команда quit Вече може да премахнете временната функционалност, където ако реда започва с `[Q]` програмата спира и изкарва целия текст. Добавете командата `[Q]`, която изкарва на екрана целия текст (без номера на редове) и спира програмата. =[Примери:]= *[Смесен вход/изход]* ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high :Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high :Q 1 2 3 ; Excess parameters DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high ### д) команда delete Имплементирайте функцията `[deleteRow]`, която получава целия текст, въведен до сега, и номер на реда (редовете се индексират от 1 до N). Тя променя текста, като премахва реда на дадения номер. .important Не забравяйте да промените размера на масива с низове! Не е решение просто да промените указателя към дадения ред на `[nullptr]`, не искаме да използваме излишна памет. .question Какъв ще бъде типа на аргумента, който приема целия текст? Добавете командата `[D]`, която приема един параметър - цяло положително число, и го прилага върху функцията `[deleteRow]`. Ако номера на реда е невалиден, трябва да изкарате съобщение "; Invalid row number". Имплементирайте следните функционалности за всички команди: .bulleted - Ако срещнете команда, на която не са и подадени нужния брой параметри, изкарайте съобщението "; Not enough parameters" и продължете изпълнение. - Ако даден параметър на команда е от невалиден тип (подадени букви, когато се иска число, примерно), изкарайте "; Invalid parameter type". Единствените типове на параметри са цели числа и произволни низове (без шпации). =[Пример:]= *[Смесен вход/изход]* ```terminal dAY HAD DAWNED COLD AND GRAY WHEN :P 1 dAY HAD DAWNED COLD AND GRAY WHEN :D 1 :P DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. :P 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- 4 est. It was a high bank, and he paused to breathe at the top. :D 0 ; Invalid row number :D 8 ; Invalid row number :D A ; Invalid parameter type :D 4 8 9 ; Excess parameters :P 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- :Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- ### e) команда insert Имплементирайте функция `[insertRow]`, която приема целия текст, низ и номер на реда. Функцията вмъква низа в целия текст като ред =[над]= този на подадения номер. Ако номерът е над броя въведени редове до сега, редът се вмъква като последен. Добавете команда `[O]`, която приема един параметър - неотрицателен ред. Следващия написан ред ще се вмъкне преди реда на дадения номер, използвайки функцията `[insertRow]`. Ако номера е невалиден изкарва "; Invalid row number". =[Пример:]= *[Смесен вход/изход]* ```terminal the man turned aside from the main Yukon trail. He climbed the high :P 1 the man turned aside from the main Yukon trail. He climbed the high :O 1 DAY HAD DAWNED COLD AND GRAY WHEN :P 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high :O 0 ; Invalid row number est. It was a high bank, and he paused to breathe at the top. :P 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 est. It was a high bank, and he paused to breathe at the top. :O 3 earth-bank where a little-traveled trail led east through the pine for- :P 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- 4 est. It was a high bank, and he paused to breathe at the top. :O 10 He excused :Q 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- 4 est. It was a high bank, and he paused to breathe at the top. 5 He excused ### ж) команда join Имплементирайте функция `[joinRows]`, която приема текстът, въведен до сега, и номер на ред N. Функцията вмъква текста от ред N+1 в края на ред N, като ги разделя с една шпация. Ред N+1 се изтрива. Ако N е 0 или номера на последния ред, не прави нищо. .important Не забравяйте да промените размера на масива с низове! Не е решение просто да промените указателя към дадения ред на `[nullptr]`, не искаме да използваме излишна памет. Добавете команда `[J]`, която приема номер на ред - положително число. Следващия ред ще се вмъкне в края на сегашния, с една шпация между тях, използвайки функцията `[joinRows]`. При подаден невалиден ред изкарвате "; Invalid row number". =[Пример:]= *[Смесен вход/изход]* ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high :P 1 DAY HAD DAWNED 2 COLD 3 AND GRAY WHEN 4 the man turned aside from the main Yukon trail. He climbed the high :J 2 :P 1 DAY HAD DAWNED 2 COLD AND GRAY WHEN 3 the man turned aside from the main Yukon trail. He climbed the high :J 1 :P 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high :J 0 :J 2 :J 8 ; Invalid row number :Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high ### з) команда word info Имплементирайте функция `[wordOccurrences]`, която приема целия текст и дума (низ без шпации). Тя изкарва на екрана броя на срещания на дадената дума в целия текст, като изхода е във формата "; N occurrences" (където N е броя на срещания). *[Подсказвам, че за следващата подточка ще е полезно ако първо имплементирате функция, която връща броя срещания на дума в един ред.]* Добавете команда `[n]`, която приема един аргумент - низ беш шпации. Използвайки `[wordOccurrences]` изкарва броя срещания на дадена дума в целия текст. =[Пример:]= *[Смесен вход/изход]* ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. :n the ; 6 occurrences :n earth ; 0 occurrences :n earth-bank ; 1 occurrences :n . ; 3 occurrences :Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. ### и) команда word substitute Имплементирайте функция `[substituteWord]`, която приема целия текст и две думи (низове без шпации). В текстът, всяко срещане на първата дума е заменено с втората дума. .question Какво ще стане с размера на един ред, ако някоя дума/някои думи трябва да се заменят? Добавете команда `[s]`, която приема две думи - низове без шпации. Използвайки функцията `[substituteWord]` замества всяко срещане на първата дума с втората. ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. :s the of :p 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 of man turned aside from of main Yukon trail. He climbed of high 3 earth-bank where a little-traveled trail led east through of pine for- 4 est. It was a high bank, and he paused to breaof at of top. :s of the 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail. He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- 4 est. It was a high bank, and he paused to breathe at the top. :s . ! 1 DAY HAD DAWNED COLD AND GRAY WHEN 2 the man turned aside from the main Yukon trail! He climbed the high 3 earth-bank where a little-traveled trail led east through the pine for- 4 est! It was a high bank, and he paused to breathe at the top! :Q DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. ### й) команда word delete Имплементирайте функция `[deleteWord]`, която приема целия текст и дума (низ без шпации). В текстът, всяко срещане на думата, заедно с *[излишните]* шпации около нея, са премахнати. Ето в кои случаи шпации са излишни (където "WORD" е подадената дума, която ще изтрием, а "\_" е някаква буква, която не е шпация): .bulleted - `[WORD _]` (WORD е в началото на реда или има знаци преди нея) - шпацията след думата е излишна, трябва да стане `[_]`. Отбелязвам, че шпациите в ляво се запазват: `[ WORD _]` става `[ _]`. - `[_ WORD]` (WORD е в края на реда или има знаци след нея) - шпацията преди думата е излишна, трябва да стане `[_]`. - `[_ WORD _]` - шпацията, която следва думата, е излишна, тоест трябва да стане `[_ _]`. Трябва да отбележа, че шпациите в ляво се запазват така както са: `[_ WORD _]` става `[_ _]`. Във всичките случаи, като имам предвид "шпацията е излишна", означава че тази шпация, заедно с всички съседни. Тоест, `[WORD _]` трябва да стане `[_]`, а не `[ _]`. Добавете команда `[d]`, която приема един параметър - дума, низ без шпации. Използвайки функцията `[deleteWord]` премахва самата дума и излишните шпации. ```terminal DAY HAD DAWNED COLD AND GRAY WHEN the man turned aside from the main Yukon trail. He climbed the high earth-bank where a little-traveled trail led east through the pine for- est. It was a high bank, and he paused to breathe at the top. :d the :Q DAY HAD DAWNED COLD AND GRAY WHEN man turned aside from main Yukon trail. He climbed high earth-bank where a little-traveled trail led east through pine for- est. It was a high bank, and he paused to brea at top.