# Задачи - ООП, Седмица 4, 14.03.2024 \n GitHub classroom: [url https://classroom.github.com/a/qa_FfWeG classroom.github.com/a/qa_FfWeG] ## Преговорни ### Задача 1 - Капсулация .solution-link [url https://github.com/Syndamia/oop-2023-solutions/blob/main/week04/Exercise1.cpp Решение] Имплементирайте структура `[Smartphone]`, която запазва =[скрито]=: .bulleted - марка, низ с максимална дължина от 128 знака - модел, низ с максимална дължина от 512 знака - година на произвеждане, неотрицателно целочислено число - резолюция на камера, число с плаваща запетая (обозначаващо мегапиксели) За всяка стойност напревете съответните get-ъри и set-ъри, правейки следните проверки при set-ърите: .bulleted - марката и моделът не могат да бъдат празни низове, или пък да надвишават максималната дължина - годината трябва да бъде между 2000 и 2024 - резолюцията не може да бъде отрицателна (може да бъде нула, което показва, че смартфонът няма камера) При неизпълнено условие, хвърляте грешка. ### Задача 2 - Капсулация с динамична памет .solution-link [url https://github.com/Syndamia/oop-2023-solutions/blob/main/week04/Exercise2.cpp Решение] Имплементирайте структура `[Bee]`, която запазва възрастта на пчела чрез число с плаваща запетая и типа пчела с буква. Имплементирайте структура `[BeeHive]`, която запазва динамично-заделен масив с всички реещи се пчели и друг динамично-заделен масив с всички яйца в кошера. Размерите на двата масива се подават на конструктора. Имплементирайте нужните конструктор и деструктор. ## Лесни задачи ### Задача 3 .solution-link [url https://github.com/Syndamia/oop-2023-solutions/blob/main/week04/Exercise3.cpp Решение] Имплементирайте структура `[Paper]`, която запазва своето текстово съдържание като низ от максимум 1024 знака и положително цяло число, определящо номера на страницата. От входа получавате на един ред цялото текстото съдържание за един обект от тип `[Paper]` и на следващия ред - бройките копия `[N]` на дадения обект. Създайте `[Paper]` обект със съответното съдържание и номер на страницата `[1]`. Създайте динамично-заделен масив от `[Paper]` с размер `[N]`, като първия му елемент е новосъздадения обект, докато останалите са =[копия]= на първия обект. При всяко копие, трябва да увеличите номера на страницата. Имплементирейте логиката чрез копиращ конструктор. ### Задача 4 .solution-link [url https://github.com/Syndamia/oop-2023-solutions/blob/main/week04/Exercise4.cpp Решение] Създайте структура `[DynamicString]`, чиито конструктор приема низ с терминираща нула, заделя точно толкова динамична памет, колкото е нужно да се запази целия низ и копира буквите на низа в тази памет. Имплементирайте оператор равно. .question Какви данни трябва `[DynamicString]` да запазва скрито? :question Какво трябва оператор равно да направи, ако записваме в `[DynamicString]` с вече заделена памет?\n Тоест ако имахме:\n `[DynamicString s1("Hello"); DynamicString s2("World"); s2 = s1;]` ### Задача 5 .solution-link [url https://github.com/Syndamia/oop-2023-solutions/blob/main/week04/Exercise5.cpp Решение] Имплементирайте структура `[TVProgram]`, която запазва името на предаването като низ от максимум 1024 знака, начало на излъчване и край на излъчване като неотрицателни целочислени числа (като примерно 1347 е един часа и 47 минути следобед). Имплементирайте конструктор, деструктор, оператор равно и копиращ конструктор. Имплементирайте структура `[TVChannel]`, която запазва динамично заделен масив от `[TVProgram]`, размера на динамично заделената памет и броя "ненулеви" елементи (програми, добавени с `[AddProgram]`). Имплементирайте нейн метод `[AddProgram]`, който приема `[TVProgram]` =[по копие]= и го вмъква на последната свободна позиция в масива. Ако масива е пълен, трябва да го "оразмерите" (да направите нов, по-голям масив, да копирате данните от стария в новия, да изтриете стария и да обновите указателя да сочи към новия). .question Кога използвате копиращия конструктор на `[TVProgram]` и кога използвате оператор равно? ## Трудни задачи ### Задача 6 Ще разработим (изключително груба) симулация на вселената. За нас, гравитацията няма да бъде сила, която просто привлича тела към себе си, а сила която кара телата около нея да се въртят ("орбитират") в перфектен кръг. Имаме много звезди и една планета, като звездите са винаги неподвижни, а планетата се влияе от тях. Гравитационното привличане на звезда в своя център се определя от ъгъла θmax (в градуси). Планетата се върти около една звезда, използвайки стандартната матрица за ротация: [image ./img/Rotation_matrix.png] Ъгълът на въртене θ, спрямо разстоянието до една звезда, се определя чрез [url https://en.wikipedia.org/wiki/Inverse-square_law закона на обратните квадрати], тоест в зависимост от разстоянието `[d]` между центъра на звездата и центъра на планетата, то истинският ъгъл на завъртане е θ = θmax * 1 / d^2. Допълнително, ако имаме повече от една звезда, тогава ще използваме θ' = max(θi - average(θ1, ..., θn)), където θi е намереният ъгъл θ за i-тата звезда и имаме n на брой звезди. Ефектът на това е, че ако имаме две звезди на еднакво разстояние с еднакъв ъгъл, тогава планетата е неподвижна, а ако някоя планета е с малко по-близка, тогава се върти около нея и то съвсем бавно. Приемаме, че отнема единица време планетата да се завърти с ъгъл θ', без значение размера на ъгъла. Целта на задачата е да върнете при коя звезда и за колко единици време планетата е успяла да извърши пълна ротация (разбира се, θ' и планетата може да се измени след всяка ротация). Имплементирайте структури: .bulleted - `[Matrix2x2]` и `[Matrix2x1]`, чиито стойности са числа с плаваща запетая, и с член функции за събиране и умножение (не оператор+, оператор\*) - `[Coordinate]`, която запазва (=[не наследява]=) точките в пространството като `[Matrix2x1]` и имплементира събиране, умножение и разстояние между координати и матрици - `[Star]`, запазваща координатата на своя център (`[Matrix2x1]`) и ъгълът θmax като число с плаваща запетая. Имплементирайте и метод, който приема планета и връща ъгълът θ. - `[Planet]`, запазваща своите координати (`[Matrix2x1]`) и изминалото време (тоест колко пъти се е движела от началото на симулацията). Имплементирайте метод `[OrbitPlanet]`, която приема планета и ъгъл θ', и се завърта около нея. - `[Universe]`, запазваща всички звездите и планетата. Имплементирайте метод `[FullOrbit]`, която връща звездата около която планетата е успяла да извърши пълна ротация и времето за което това се е случило.