Summary Files Commits Branches @commit @diff @stats
path: root / src / teaching / upp-2023 / week2 / index.du
blob: 645f1c6af0230f3c26e43c470ce4b48b552bd684 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
# Задачи - УПП, Седмица 2, 13.10.2023

\n

GitHub classroom: [url https://classroom.github.com/a/Bi5dhwW7 classroom.github.com/a/Bi5dhwW7]

Решения: [url https://github.com/Syndamia/upp-2023-solutions/tree/main/week02 GitHub]

## [=Важни бележки=]

.numbered
1. Не е добре да ползвате [`using namespace std;`]
2. Единствената библиотека, която (поне за сега) може да ползвате е [`iostream`]
3. За хората с текстови редактори и [`gcc`], моля да погледнете в Moodle и да използвате предоставените флагове, най-важния от които е [`-std=c++17`]
3. Като си качвате решенията в GitHub classroom, за предпочитане е имената на файловете да свършват на [`.cpp`].
   Отново, не е задължително, но ми улеснява живота.

## Тема: конвертиране

\n

### Задача 1 - Конвертирания от int

Получавате целочислено число (тип [`int`]), след това, за всеки тип от следния списък, трябва да изкарате на нов ред текст във формата "Със/без загуба тип стойност":

.bulleted
- [`bool`]
- [`long long int`]
- [`unsigned int`]
- [`char`]
- [`short int`]
- [`double`]
- [`long int`]
- [`unsigned char`]

Целта е да напишете един низ, който съдържа "Със/без загуба тип", и след това да изкарате (конвертираната) стойност.
Не се иска да правите код, който намира тази информация автоматично, всичко това просто си го напишете ръчно (hardcoded).

[=Пример=]
  [*Нарочно са показани само първите два реда от изхода*]

:table_2
|= Вход
|= Изход

|: 5
|: Със загуба bool 1\nБез загуба long long int 5\n...


## Тема: Побитови оператори

\n

### Задача 2 - Mask

Получавате положително цяло число, от него трябва да "запазите" само първите (най-десните) 6 бита и да изкарате получилото се число.

[=Примери=]

:table_2
|= Вход
|= Изход

|: 5
|: 5

|: 200
|: 8


### Задача 3 - Деление и умножение

Получавате положително цяло число [`а`], трябва да изкарате две числа (разделени с празно пространство):\n
[`a`] (целочислено) разделено на 16 и [`а`] умножено по 8.
[=Трябва да използвате побитови оператори за това!=]

[=Пример=]

:table_2
|= Вход
|= Изход

|: 73
|: 4 584


### Задача 4 - IP адрес

Разграничаваме устройствата, свързани към интернет, по техния IP адрес.
Това е едно най-обикновено цяло без-знаково 32-битово число.
Да се гледа като число не е удобно, заради това (и други причини, които ще учите във втори курс) IP адресът се изписва във формата "a.b.c.d", като a, b, c и d са съответно десетичното представяне на всички осморки битове.

Тоест, един валиден адрес би бил числото "2155905152", което разглеждайки по битове изглежда така:

```
10000000100000001000000010000000

Разделяйки по осморки битове:

```
10000000 10000000 10000000 10000000

Всяка като я превърнем в десетично число става:

```
128 128 128 128

И накрая изкарания резултат трябва да бъде [`128.128.128.128`]

На входа получавате цяло положително число, трябва да изкарате на екрана как би изглеждало с това представяне, с точките между осморки битове.

[=Примери=]

:table_2
|= Вход
|= Изход

|: 3831791750
|: 228.100.128.134

|: 240
|: 0.0.0.240

|: 948405232
|: 56.135.131.240


## Тема: Логически оператори

\n

### Задача 5 - Дели ли се

От входа получавате две числа: [`а`] и [`n`].
Трябва да върнете 0 ако [`a`] не се дели на [`n`] без остатък, и 1 иначе.

[=Упътване:=] Булевата стойност [`false`] се изкарва като 0, а [`true`] се изкарва като 1, от [`std::cout`]

[=Примери=]

:table_2
|= Вход
|= Изход

|: 200 10
|: 1

|: 91 5
|: 0



### Задача 6 - Цифра ли е

Получавате от входа буква, трябва да върнете 0 ако буквата не е цифра и 1 ако е.

[=Примери=]

:table_2
|= Вход
|= Изход

|: 5
|: 1

|: a
|: 0

|: !
|: 0


## Тема: Условни конструкции

\n

### Задача 7 - Нарастващ ред

На входа получавате три целочислени, трябва да ги изкарате в нарастващ ред.

[=Пример=]

:table_2
|= Вход
|= Изход

|: 5 3 8
|: 3 5 8


### Задача 8 - Календар

От входа получавате число от 1 до 12: номера на месеца.
Трябва да изкарате името на месеца, където 1 съответства на "January", 2 на "February" и так. нат.
Моля използвате [`switch`] конструкция.

[=Примери=]

:table_2
|= Вход
|= Изход

|: 1
|: January

|: 10
|: October


### Задача 9 - Монети

Получавате число с плаваща запетая, това ще бъде цената на даден продукт в лева.
Искате да платите използвайки само монети, като целта е да използвате възможно най-големите стойности на монети, възможно най-много (тоест ситуацията в която трябва да носите един милион монети по една стотинка не трябва да е възможност).
Изкарайте двойки "монета бройка", като работите с монети от по 50 стотинки, 20 стотинки, 10 стотинки, 5 стотинки, 1 стотинка.

[=Примери=]

:table_2
|= Вход
|= Изход

|: 12.0
|: 0.5 24 0.2 0 0.1 0 0.05 0 0.01 0

|: 3.37
|: 0.5 6 0.2 1 0.1 1 0.05 1 0.01 2


### Задача 10 - ILS

При кацане, един самолет се нужда от информация дали е точно приравнен със средата на пистата, особено когато видимостта е занижена.
Една система за тази цел се нарича [url https://www.pilotscafe.com/Understanding-ILS/ ILS], но ние ще разгледаме нейния компонент, [url https://en.wikipedia.org/wiki/Instrument_landing_system_localizer the localizer]: в края на пистата големи предаватели излъчват различни радио сигнали в двете половини на пистата.

Ефектът е като на стерео тон колони, когато самолетът е в ляво от пистата, той приема сигнала от лявата част на пистата по-силно от този за дясната, както ако си доближиш ухото до лявата тон колона, ти ще чуваш нейния звук по-силно от дясната.

Получавате едно цяло положително число, то ще е във формата "XXXYYY", където "XXX" е три-цифрено число, което съдържа интензитета на сигнала от лявата половина, и аналогично "YYY" е три-цифрено число, което е интензитета от сигнала на дясната половина.

Спрямо техните стойности, трябва да върнете "Turn right" ако самолетът е в ляво от пистата (ако XXX е по-голямо от YYY) и "Turn left" ако самолетът е в дясно.
Допълнително, понеже не е нужно самолетът да се намира перфектно в средата на пистата, зачитаме че ако разликата между двата интензитета е по-малка от 4, тогава самолетът е правилно подравнен и връщаме "Follow heading".

[=Примери=]

:table_2
|= Вход
|= Изход

|: 045093
|: Turn left

|: 100090
|: Turn right

|: 050053
|: Follow heading


### Задача 11 - GPS

[*В тази задача има много "теория", иначе самия код е малък и лесен.*]

Кондензирайки възможно най-много, ще обясня как работи GPS.
На земята имаме специални методи, чрез които можем да определим позицията на всеки сателит, обаче обратното, определянето на позицията чрез сателит, става с помощта на супер прецизни часовници и малко математика.

Понеже радио комуникацията е със скоростта на светлината, можем лесно да определим разстояния между сателит и дадена точка, считайки колко време е отнело на сателита да върне отговор (припомням формулата [`s = v * t`], или [`разстояние = скорост * време`]).

Обаче, така получаваме само разстоянието, това не е достатъчно за да определим точната позиция, понеже има много възможни точки на земята, които да са на това разстояние.
Решението на проблема, е че просто вземаш разстоянието от няколко сателита, твоята позиция се намира в общата точка между всички възможни области.

С други думи, наш приятел ни се обажда, иска да разбере къде се намира.
Ние знаем на кой адрес се намираме, и приятеля ни знае само, че се намира на 300 метра от нас.
Този приятел също се е свързал със съседката и е казал, че се намира на 299 метра от нея.
Нека да нарисуваме два кръга върху една карта, за всички възможни места, където той може да се намира спрямо нашият и на съседката адрес.
Тези кръгове ще се пресичат, и знаем, че той може да се намира само в някоя от пресечените позиции.

От математика, ако знаем разстоянието на нашия приятел към трети различен човек, трите кръга върху картата ще се пресичат в само една точка, а именно позицията на нашия приятел.
В три измерения, правим същото, обаче със сфери, и ни трябват четири сателита.
Понеже математиката в две и три измерения е малко множко, ще разгледаме всичко едноизмерно, в [url https://en.wikipedia.org/wiki/Flatland Lineland].

\n

Разработваме (сериозно опростена) GPS система, като работим с едноизмерни координати, тоест позицията на всичко се определя с по едно число.
Изпращаме съобщение към два сателита по едно и също време, и получаваме отговор (какво е съобщението и отговор не е важно, интересува ни само времето).
Считайки нужното време да получим отговор, намираме разстоянията, от там ще имаме общо 4 възможности, като 2 от тях ще се препокриват и това ще бъде нашата позиция.

От входа получавате число, което е точното време в милисекунди спрямо денонощието, в което сме изпратили съобщение към двата сателита.
След това получавате още две числа, координата на първия сателит и по кое време в милисекунди спрямо денонощието е получен отговора.
Накрая получавате още две числа, пак координата и време, но за втория сателит.
Изкарайте къде се намираме ние, като нека скоростта на светлината да бъде 29 метра в милисекунда.

[=Пример=]

:table_2
|= Вход
|= Изход

|: 18 -100 22 132 30
|: -42