-
Notifications
You must be signed in to change notification settings - Fork 0
/
topic_1_01.html
766 lines (728 loc) · 70.9 KB
/
topic_1_01.html
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
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
<!DOCTYPE html>
<html lang="ru">
<head>
<title>1.01 - Парадигмы программирования. Основы объектно-ориентированного подхода</title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
<style>
body {
background: #dfdfdf;
}
/* Remove the navbar's default margin-bottom and rounded borders */
.jumbotron {
padding-top: 0;
padding-bottom: 0;
}
#header {
background-color: #445566;
}
#header h2, #header h4, #header h3, #header h5, #header p {
margin-left: -10px;
color: #ededed;
}
#header h2 {
font-weight: bold;
}
#header h4 {
font-size: 1.5em;
}
#content {
background: white;
padding-right: 9%;
box-sizing: border-box;
}
p {
text-align: justify;
}
img {
max-width: 100%;
}
ul.nav, ul.side_menu {
list-style-type: none;
margin-left: -20px;
}
.navbar {
margin-bottom: 0;
border-radius: 0;
}
.navbar-inverse {
background-color: #445566;
border: none;
border-top: 1px solid white;
}
.navbar-inverse .navbar-nav > .active > a, .navbar-inverse .navbar-nav > .active > a:hover, .navbar-inverse .navbar-nav > li > a:hover {
background-color: #293b4c;
}
/* Set height of the grid so .sidenav can be 100% (adjust as needed) */
.row.content {
height: 450px
}
/* Set gray background color and 100% height */
.sidenav {
padding-top: 20px;
height: 100%;
}
.btn-info {
color: #fff;
background-color: #445566;
border: none;
border-radius: 0;
margin-top: 5px;
margin-bottom: 5px;
}
.btn-info:hover {
background-color: #293b4c;
}
.navbar-inverse .navbar-toggle:hover{
background-color: #293b4c;
}
.hide{
visibility: hidden;
}
.disa{
cursor: default;
opacity: 0.6;
}
.disa:hover{
background-color: #445566;
}
/* Set black background color, white text and some padding */
footer {
background-color: #293b4c;
color: white;
padding: 15px;
}
#up{
color: #fff;
position: fixed;
display: block;
background: #293b4c;
width: 40px;
height: 40px;
bottom: 64px;
right: 30px;
opacity: 0;
border-radius: 50%;
padding-left:12px;
padding-top: 8px;
box-sizing: border-box;
}
/* On small screens, set height to 'auto' for sidenav and grid */
@media screen and (max-width: 990px) {
#content {
padding-right: 10px;
}
#up {
display: none !important;
}
}
/* On small screens, set height to 'auto' for sidenav and grid */
@media screen and (max-width: 767px) {
.sidenav {
height: auto;
padding: 15px;
}
.row.content {
height: auto;
}
}
@media only screen and (max-width: 600px) {
img.small_img {
width: 40%;
height: auto;
}
img.big_img {
width: 90%;
height: auto;
}
}
</style>
</head>
<body id="top">
<div class="container-fluid text-left" id="header">
<div class="container text-left col-md-3 col-sm-12">
<img src="Images/icon-java.png" style="padding-top: 15px; box-sizing: border-box;">
</div>
<div class="container text-left col-md-9 col-sm-12">
<h2>Язык программирования и технологии Java</h2>
<h5>Разработчик курса Л. В. Иванов</h5>
<h4>Модуль 1 Объектно-ориентированное программирование и язык Java</h4>
</div>
</div>
<nav class="navbar navbar-inverse">
<div class="container-fluid">
<div class="navbar-header">
<button type="button" class="navbar-toggle" data-toggle="collapse" data-target="#myNavbar">
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
</div>
<div class="collapse navbar-collapse" id="myNavbar">
<!--div class="col-sm-12 col-md-3 sidenav">
</div-->
<ul class="nav navbar-nav">
<li ><a href="index.html">Главная</a></li>
<li class="active"><a href="">Объектно-ориентированное программирование и язык Java</a></li>
<li><a href="topic_2_01.html">Платформа Java SE</a></li>
<li><a href="">Разработка приложений JAVA EE</a></li>
</ul>
</div>
</div>
</nav>
<div class="container-fluid text-left">
<div class="row content">
<div class="col-sm-12 col-md-3 sidenav">
<ul class="side_menu">
<li>1 Объектно-ориентированное программирование и язык Java
<ul class="side_menu">
<li>01 Парадигмы программирования. Основы объектно-ориентированного подхода</li>
<li><a href="topic_1_02.html">02 Язык программирования Java и Java-платформа</a></li>
<li><a href="topic_1_03.html">03 Синтаксические конструкции языка Java</a></li>
<li><a href="topic_1_04.html">04 Ссылочные типы. Массивы. Строки и классы-оболочки</a></li>
<li><a href="topic_1_05.html">05 Определение классов. Наследование и полиморфизм</a></li>
<li><a href="topic_1_06.html">06 Вложенные типы. Интерфейсы. Лямбда-выражения и ссылки на методы</a></li>
<li><a href="topic_1_07.html">07 Перечисления. Исключения. Использование обобщений</a></li>
<li><a href="topic_1_08.html">08 Понятие паттернов проектирования. Порождающие паттерны</a></li>
</ul>
</li>
<li>2 Платформа Java SE
<ul class="side_menu">
<li><a href="topic_2_01.html">01 Платформа Java SE и ее составляющие</a></li>
<li><a href="topic_2_02.html">02 Работа с коллекциями в Java 7</a></li>
<li><a href="topic_2_03.html">03 Работа с текстовыми данными. Локализация</a></li>
<li><a href="topic_2_04.html">04 Работа с потоками ввода-вывода и файловой системой</a></li>
<li><a href="topic_2_05.html">05 Работа с XML. XML-сериализация</a></li>
<li>06 Тестирование и управление сборкой. Ведение системного журнала</li>
<li>07 Работа с потоками выполнения</li>
<li>08 Работа с контейнерами Java 8. Stream API</li>
<li>09 Поддержка сетевого взаимодействия</li>
<li>10 Работа с базами данных</li>
<li>11 Использование RTTI и рефлексии. Метапрограммирование. Аннотации</a></li>
<li>12 </a>Использование структурных паттернов</li>
</ul>
</li>
<li>3 Основы разработки приложений Java EE
<ul class="side_menu">
<li>01 Платформа Java EE. Web-приложения. Создание сервлетов</li>
<li>02 Основы создания страниц JSP</li>
<li>03 Работа с EJB. Создание Web-сервисов</li>
<li>04 Использование Spring Framework</li>
<li>05 Использование паттернов поведения и распределения ответственности </li>
<li>06 Дополнительные возможности Java 11</li>
</ul>
</li>
</ul>
</div>
<div class="col-sm-12 col-md-9 text-left" id="content">
<div class="w3-clear nextprev">
<a class="btn btn-info float-left" href="index.html">Предыдущая</a>
<a class="btn btn-info float-left" href="topic_1_02.html">Следующая</a>
</div>
<h1>Парадигмы программирования. Основы объектно-ориентированного подхода</h1>
<h2>1 Теоретическая часть</h2>
<h3>1.1 Парадигмы программирования </h3>
<p><i>Парадигма программирования</i> (programming paradigm) – это совокупность идей и понятий,
определяющих стиль написания компьютерных программ. Это способ концептуализации, определяющий
организацию вычислений и структурирование работы, выполняемой компьютером.</p>
<p>Первоначальный подход к программированию не основывался какой-либо методологии. Программа состояла из
последовательно выполняемых команд, а также меток, условного и безусловного перехода. Современная
методология программирования включает большое количество парадигм, наиболее распространенными из которых
являются следующие:</p>
<ul>
<li><i>Императивное программирование</i> (imperative programming) описывает процесс получения
результатов как последовательности инструкций изменения состояния программы.
</li>
<li><i>Функциональное программирование</i> (functional programming) рассматривает вычисление как
последовательность вызовов функций без сохранения состояния приложения.
</li>
<li><i>Структурное программирование </i> (structured programming) определяет действия программы, которые
необходимо принять для достижения желаемого результата.
</li>
<li><i>Процедурное программирование</i> (procedural programming) предусматривает функциональный подход с
хранением состояния программы.
</li>
<li><i>Модульное программирование</i> (modular programming) предусматривает разделение программы на
независимые логические и физические части, которые могут самостоятельно обрабатываться.
</li>
<li><i>Компонентное программирование</i> (component-based programming) предусматривает сохранение
модульной структуры программного обеспечения при выполнении программы.
</li>
<li><i>Объектно-ориентированное программирование</i> (ООП, object-oriented programming) организует
программу как совокупность объектов (структур данных, состоящих из полей данных и методов), а также
их взаимодействия.
</li>
<li><em>Прототипное программирование</em> (prototype-based programming) – разновидность
объектно-ориентированного программирования, реализованного не через классы, а через наследование
объектов производится путём клонирования существующего экземпляра объекта (прототипа).
</li>
<li><i>Обобщенное программирование</i> (generic programming) заключается в таком описании данных и
алгоритмов, которое можно применять к различным типам данных, не меняя это описание.
</li>
<li><i>Событийно-ориентированное программирование</i> (event-driven programming) – управления
вычислениями определяется через события (асинхронный ввод и сообщение из других программ или потоков
и т.п.).
</li>
<li><i>Метапрограммирование</i> (metaprogramming) предусматривает создание программ, которые порождают
другие программы как результат своей работы, или программ, которые изменяют себя во время
выполнения.
</li>
<li><i>Декларативное программирование</i> (declarative programming) определяет логику вычисления без
описания потока управления.
</li>
</ul>
<p>Существует также много других парадигм программирования – автоматное, аспектно-ориентированное,
функционально-ориентированное и т. д.</p>
<h3>1.2 Методология императивного программирования</h3>
<h4>1.2.1 Основные концепции</h4>
<p><i>Императивное программирование</i> – это парадигма программирования, согласно которой описывается
процесс получения результатов как последовательность инструкций изменения состояния программы. Чаще
императивное программирование, в котором определяется необходимая последовательность действий,
противопоставляют декларативному программированию, которое предусматривает определение того, что мы
желаем получить. В отличие от функционального программирования, императивная парадигма предполагает
наличие состояния, которое может храниться, например, с помощью глобальных переменных.</p>
<p>Кроме первоначального (неструктурного) подхода, к императивному программированию относят процедурное и
модульное программирование. Кроме того, в пределах объектно-ориентированной методологии императивный
подход используют для реализации методов классов.</p>
<p>Для реализации "неструктурного" подхода в языке программирования необходимо наличие следующих
средств:</p>
<ul>
<li>описание переменных;</li>
<li>последовательное выполнение утверждений, в частности присвоение переменным определенных значений;
</li>
<li>метки;</li>
<li>безусловный переход (<code><b>goto</b></code>);</li>
<li>условный переход (<code><b>if</b>...<b>goto</b></code>).</li>
</ul>
<p>Вследствие отсутствия в языке Java оператора goto реализация такого "неструктурного" подхода на
Java невозможна.</p>
<h4>1.2.2 Реализация структурного подхода</h4>
<p><em>Структурное программирование</em> – это парадигма, предполагающая написание программы как набора
блоков. Такими блоками являются ветвления, циклы, последовательность утверждений. Благодаря наличию
циклов с предусловием, постусловием и с параметром программа может полностью быть реализована без
условных и безусловных переходов.</p>
<p>Современные языки структурного программирования поддерживают отдельную область видимости блоков (внутри
блоков могут создаваться локальные переменные, константы, типы и т.д.).</p>
<p>Реализация структурного программирования в Java базируется на использовании следующих конструкций:</p>
<ul>
<li>последовательное выполнение (аналогичное неструктурному программированию);</li>
<li>разветвление – условное утверждение (<b><code>if</code></b>, <b><code>if</code></b><code>...<b>else</b></code>)
и переключатель (<code><b>switch</b></code>);
</li>
<li>циклы: с предусловием (<code><b>while</b></code>), с постусловием
(<b><code>do</code></b><code>...<b>while</b></code>), с параметром (<b><code>for</code></b>);
</li>
<li>программный блок – одно или несколько утверждений, взятых в фигурные скобки; блок определяет
свою область видимости; внутри блока можно описывать переменные и константы; блоки можно вкладывать
один в другой.
</li>
</ul>
<h4>1.2.3 Реализация процедурного подхода</h4>
<p>Реализация процедурного программирования предполагает наличие в языке программирования понятия
подпрограммы (процедуры, функции), определяющей собственную область видимости и возвращающей
определенный результат, а также средств вызова функций с последующим использованием этого результата.
При вызове подпрограммы управление передается из точки вызова в код подпрограммы, а затем возвращается в
точку вызова для выполнения последующих инструкций.</p>
<p>Для размещения данных отдельных подпрограмм (функций) в памяти компьютера, отведенной для приложения,
организуется так называемый <em>программный стек</em> (стек вызовов) – область памяти,
организованная по принципу стека (LIFO, last in – first out, "последним пришел – первым
вышел"). В программном стеке хранится информация, необходимая для возврата управления из
подпрограмм в вызывающую подпрограмму (основную программу), в частности, адрес точки возврата. Кроме
адресов в программном стеке могут храниться аргументы подпрограмм, локальные переменные и другие
временно создаваемые данные.</p>
<p>В языке Java процедурный подход реализован через использование статических функций, находящихся в области
видимости классов.</p>
<h4>1.2.4 Реализация модульного подхода</h4>
<p>Модульное программирование предполагает разделение программного кода на отдельные модули, содержащие
логически связанные элементы (типы, данные, подпрограммы). На логическом уровне языки поддерживают так
называемые пространства имен. <i>Пространство имен</i> (namespace) – поименованная часть глобальной
области видимости, в которой могут содержаться объявления и определения. Пространства имен помогают
избежать конфликтов имен. </p>
<p>На физическом уровне в качестве модулей могут выступать библиотеки, сборки, объектные модули и т. д. (в
зависимости от языка программирования и программной платформы).</p>
<p>Для реализации модульного подхода в Java используются пакеты, обеспечивающие группировку кода как на
логическом, так и на физическом уровне.</p>
<h3>1.3 Причины возникновения и преимущества объектно-ориентированного подхода</h3>
<p>В семидесятые годы ХХ века индустрия разработки программного обеспечения столкнулась с вызовами,
обусловленными существенным повышением сложности программных систем. Возникновение диалоговых систем с
механизмами поведения привело к возникновению проблем, которые не могли быть решены традиционным
процедурным путем. Возможность асинхронного ввода данных не согласовывалась с концепцией
программирования, управляемого данными.</p>
<p>Программное обеспечение является по своей сути очень сложным. Сложность программных систем часто
превосходит человеческий интеллектуальный потенциал. Как утверждает один из основателей
объектно-ориентированной методологии Грейди Буч, эта сложность следует из четырех элементов:</p>
<ul>
<li>сложность предметной области;</li>
<li>сложность управления процессом разработки;</li>
<li>сложность обеспечения гибкости программного обеспечения;</li>
<li>сложность управления поведением дискретных систем.</li>
</ul>
<p>Мы можем преодолеть эти проблемы с помощью декомпозиции, абстракции и иерархии. Вместо функциональной
декомпозиции, на которой построено процедурное программирование, объектно-ориентированная парадигма
предлагает объектную декомпозицию. Кроме того, концепция классов позволяет обеспечить необходимый
уровень абстракции данных и иерархичность представления объектов.</p>
<p>Впервые термины "объекты" и "объектно-ориентированный" в современном смысле
объектно-ориентированного программирования появились исследованиях группы искусственного интеллекта
Массачусетского технологического института в конце 1950-х <code>-</code> начале 1960-х годов. Понятия
"объект" и "экземпляр" появились в глоссарии, разработанном Иваном Сазерлендом в
1961 г. и связаны с описанием светового пера (Sketchpad).</p>
<h3>1.4 Составляющие объектно-ориентированной методологии</h3>
<p>Основными составляющими объектно-ориентированной методологии являются объектно-ориентированный анализ,
объектно-ориентированное проектирование и объектно-ориентированное программирование.</p>
<p><i>Объектно-ориентированный анализ</i> предполагает создание объектно-ориентированной модели предметной
области. При этом речь идет не о проектировании классов программного обеспечения, а об использовании
аппарата объектно-ориентированной методологии для представления реальной системы.</p>
<p><i>Объектно-ориентированное проектирование</i> представляет собой процесс описания классов будущего
программного обеспечения с использованием формальных методов (как правило, графических), а также
определения взаимодействия классов и объектов. Отделение процесса проектирования от непосредственного
кодирования призвано преодолеть сложность программного обеспечения за счет контроля над связями между
отдельными сущностями и позволяет создавать ПО, допускающее коллективную разработку и повторное
использование кода. Эффективность процесса проектирования повышается за счет использования <i>проектных
образцов</i> (паттернов, шаблонов проектирования).</p>
<p><i>Объектно-ориентированное программирование</i> является одной из парадигм программирования и
предполагает непосредственное создание классов и объектов, а также определение связей между ними,
выполняемое с использованием одного из языков объектно-ориентированного программирования. </p>
<h3>1.5 Основные принципы и концепции объектно-ориентированной парадигмы</h3>
<p>Основополагающим принципом объектно-ориентированного подхода является <em>абстракция данных</em>.
Абстракция – это придание объекту характеристик, которые отличают его от всех других объектов,
четко определяя его концептуальные границы. Основная идея состоит в том, чтобы отделить способ
использования составных объектов от деталей их реализации в виде более простых объектов, подобно тому,
как функциональная абстракция разделяет способ использования функции и деталей её реализации в терминах
более примитивных функций, таким образом, данные обрабатываются функцией высокого уровня с помощью
вызова функций низкого уровня.</p>
<p>Такой подход является основой объектно-ориентированного программирования. Это позволяет работать с
объектами, не вдаваясь в особенности их реализации. В каждом конкретном случае применяется тот или иной
подход: инкапсуляция, полиморфизм или наследование. Например, при необходимости обратиться к скрытым
данным объекта, следует воспользоваться инкапсуляцией, создав, так называемую, функцию доступа или
свойство.</p>
<p>Этот принцип реализуется через понятие класса. <i>Класс</i> <code>-</code> это структурированный тип
данных, набор элементов данных различных типов и функций для работы с этими данными. <i>Объект</i>
– это экземпляр класса.</p>
<p><i>Данные объекта</i> (поля, fields, иногда <code>-</code> элементы данных, data members) <code>-</code>
это переменные, характеризующие состояние объекта.</p>
<p><i>Функции объекта</i> (методы, methods) <code>-</code> это функции, которые имеют непосредственный
доступ к данным объекта. Иногда говорят, что методы определяют поведение объекта. В отличие от обычных
(глобальных) функций, необходимо сначала создать объект и вызвать метод в контексте этого объекта. </p>
<p>Объекты характеризуются жизненным циклом. Создание объектов предусматривает вызов специальной функции
инициализации данных <code>-</code> так называемого <i>конструктора</i>. Конструкторы вызываются
непосредственно после создания объекта в памяти. Большинство языков объектно-ориентированного
программирования поддерживает механизмы корректной ликвидации объектов и с применением деструкторов. <i>Деструктор</i>
<code>-</code> это специальная функция, которая вызывается непосредственно перед удалением объекта и
освобождает системные ресурсы, которые были заняты в процессе создания и функционирования объекта.</p>
<p>Можно назвать три основных понятия, лежащих в основе объектно-ориентированного программирования. Это
инкапсуляция, наследование и полиморфизм.</p>
<p><i> Инкапсуляция</i> (сокрытие данных) <code>-</code> одна из трех парадигм объектно-ориентированного
программирования. Содержание инкапсуляции заключается в сокрытии от внешнего пользователя деталей
реализации объекта. В том числе доступ к данным (полям), которые обычно описаны с модификатором private,
осуществляется через открытые функции доступа. В UML перед элементами класса (атрибутами и операциями)
можно указать из видимости с помощью символов <code>+</code> (открытый), <code>-</code> (закрытый) и
<code>#</code> (защищенный).</p>
<p><i>Наследование</i> <code>-</code> это механизм создания производных классов от базовых. Создание
производного класса предусматривает расширение путем добавления новых полей (атрибутов) и методов. В C++
есть так называемые закрытое и защищенное наследование. Эти формы наследования позволяют ограничить
доступ к элементам базовых классов извне класса. В большинстве языков объектно-ориентированного
программирования поддерживается только открытое наследование – элементы при наследовании сохраняют
свою видимость. При этом закрытые элементы наследуются, но становятся недоступными для непосредственного
обращения в производных классах.</p>
<p><i>Полиморфизм </i> <code>-</code> это свойство классов, согласно которой поведение объектов может
определяться на этапе компиляции, а на этапе выполнения. Классы, декларирующие идентичный набор функций,
но реализованные под конкретные специфические требования, имеют название <i>полиморфных классов</i>.</p>
<p> Подключение тела функции к точке ее вызова называется <i>связыванием</i>. Если оно происходит до начала
выполнения программы, речь идет о <i>раннем связывании</i>. Этот тип связывания присущ языкам
процедурного типа, таким как C или Pascal. <i>Позднее связывание</i> означает, что подключение
происходит во время выполнения программы и в объектно-ориентированных языках зависит от типов объектов.
Позднее связывание еще называют динамическим, или связыванием времени выполнения. Для реализации
полиморфизма используется механизм позднего связывания.</p>
<p> В языках объектно-ориентированного программирования позднее связывание реализуется через механизм
виртуальных функций. <i>Виртуальная функция</i> (виртуальный метод, virtual method) <code>-</code> это
функция, определенная в базовом классе, и перекрытая в походных, так, что конкретная реализация функции
для вызова будет определяться во время выполнения программы. Выбор реализации виртуальной функции
зависит от реального (а не объявленного при описании) типа объекта. Таким образом, поведение ранее
созданных классов может быть изменено позже путем перекрытия виртуальных методов. Фактически
полиморфными являются классы, которые содержат виртуальные функции.</P>
<p>Некоторые языки (например, C++) поддерживают так называемый полиморфизм времени компиляции. Несмотря на
то, что поведение объектов определяется при компиляции, использование шаблонов позволяет определить
общее поведение шаблонных классов и специфицировать это поведение для конкретных типов.</P>
<p>С объектно-ориентированной парадигмой тесно связана концепция <em>программирования, управляемого
событиями</em>, в рамках которого общая организация программы предполагает создание и регистрацию
объектов с последующим получением и обработкой асинхронных событий и обмена сообщениями между объектами.
</P>
<h3>1.6 Унифицированный язык моделирования</h3>
<h4>1.6.1 Общие сведения </h4>
<p><i>Унифицированный язык моделирования</i> (Unified Modeling Language, UML) <code>-</code> это графическая
нотация для определения, описания, проектирования и документирования программных систем, бизнес-систем и
других систем различной природы, в первую очередь связанных с программным обеспечением. UML включает ряд
диаграмм для моделирования и проектирования сложных систем. Авторы языка – три видных исследователя
в области объектно-ориентированного анализа и проектирования Грэйди Буч (Grady Booch), Джеймс Рамбо
(James Rumbaugh) и Ивар Джекобсон (Ivar Jacobson). Графические элементы, определенные в UML,
представлены на диаграммах, которые отражают различную точку зрения на моделируемую систему.</p>
<p>Первая версия UML была принята консорциумом OMG (Object Management Group) в январе 1997 года в качестве
международного стандарта. Утвержденная же в сентябре версия UML 1.1 была принята на вооружение основными
компаниями – производителями программного обеспечения, такими, как Microsoft, IBM, Hewlett-Packard
и производителями CASE-средств, которые реализовали поддержку UML в своих программных продуктах. </p>
<p>Авторы и разработчики UML представляют его как язык для <i>определения</i>, <i>представления</i>, <i>проектирования</i>
и <i>документирования</i> программных систем, бизнес-систем и других систем различной природы. UML
определяет нотацию, представляющую собой совокупность графических объектов, которые используются в
моделях. Универсальный язык объектного моделирования UML не зависит от языков программирования и,
вследствие этого, может поддерживать любой объектно-ориентированный язык программирования. </p>
<p>Формальная спецификация последней версии UML 2.0 опубликована в августе 2005 года.</p>
<h4>1.6.2 Конструктивные блоки UML</h4>
<p><i>Сущности</i> являются основой модели. Привязку сущностей друг к другу обеспечивают <i>отношения</i>, а
<i>диаграммы</i> группируют наборы сущностей. В UML представлены четыре типа сущностей: структурные
(structural), поведенческие (behavioral), группирующие (group), аннотационные (annotational).</p>
<p>Графическое изображение отдельных структурных и поведенческих сущностей, принятое в UML, приводится ниже
в связи с диаграммами, на которых эти сущности чаще всего изображаются. Вместе с тем, большинство
элементов может присутствовать практически на всех диаграммах.</p>
<p>Единственным представителем группирующей сущности является <i>пакет</i> (package). Пакет – это
механизм общего назначения для организации элементов в виде единой группы. Структурные, поведенческие и
даже другие группирующие сущности могут быть помещены внутрь пакета. </p>
<p align="center"><img src="Images/02_Package.gif" class="small_img"></p>
<p><i>Аннотации</i> являются поясняющей и комментирующей частью UML. Единственным типом аннотационной
сущности является <i>примечание</i> (note). Аннотация соединяется пунктирной линией с сущностью, к
которой она относится:</p>
<p align="center"><img src="Images/02_Note.gif" class="big_img"></p>
<p align="left">Отношения являются основными связующими строительными блоками в UML. Имеется 4 типа
отношений:</p>
<ul>
<li>зависимость (dependency);</li>
<li>ассоциация (association); ее разновидностью является агрегирование (aggregation);</li>
<li>обобщение (generalization);</li>
<li>реализация (realization).</li>
</ul>
<p align="center"><img src="Images/02_Relationships.gif" width="319" height="101"></p>
<p>Третьим компонентом UML являются диаграммы.</p>
<p><i>Диаграмма</i> в UML <code>-</code> это графическое представление набора элементов, изображаемое в виде
связанного графа с вершинами (сущностями) и ребрами (отношениями). </p>
<p>UML 1 предлагает следующий набор диаграмм для моделирования:</p>
<ul>
<li>структурные диаграммы (structure diagrams):
<ul>
<li>диаграммы вариантов использования (use case diagrams) – для моделирования
бизнес-процессов организации (требований к системе);
</li>
<li>диаграммы классов (class diagrams) – для моделирования статической структуры классов
системы и связей между ними;
</li>
<li>диаграммы объектов (object diagrams) – для моделирования статической структуры
экземпляров классов (объектов) и связей между ними;
</li>
</ul>
<li>диаграммы поведения системы (behavior diagrams):
<ul>
<li>диаграммы взаимодействия (interaction diagrams):
<ul>
<li>диаграммы последовательности (sequence diagrams) и диаграммы коммуникаций
(communication diagrams) – для моделирования процесса обмена сообщениями между
объектами;
</li>
</ul>
</li>
<li>диаграммы состояний (statechart diagrams) – для моделирования поведения объектов
системы при переходе из одного состояния в другое;
</li>
<li>диаграммы деятельностей (activity diagrams) – для моделирования поведения системы в
рамках различных вариантов использования, или моделирования деятельностей;
</li>
</ul>
<li>диаграммы реализации (implementation diagrams):
<ul>
<li>диаграммы компонентов (component diagrams) – для моделирования иерархии компонентов
(подсистем) системы;
</li>
<li>диаграммы размещения (deployment diagrams) – для моделирования физической архитектуры
системы.
</li>
</ul>
</li>
</ul>
<p>UML 2 дополнительно предлагает следующие диаграммы:</p>
<ul>
<li>диаграммы пакетов (package diagrams) – для отображения зависимостей между пакетами,
составляющими модель;
</li>
<li>диаграммы профилей (profile diagrams) – используются для визуализации механизмов расширения;
</li>
<li>диаграммы композитной структуры (composіte structure diagrams) – для моделирования внутренней
структуры сущности;
</li>
<li>диаграммы обзора взаимодействия (іnteractіon overview diagrams) – диаграммы деятельности,
узлами которых выступают диаграммы взаимодействия;
</li>
<li>диаграммы отображения во времени (tіmіng diagrams), или диаграммы синхронизации, используются для
учета изменения состояния или значений параметров элементов при функционировании;
</li>
</ul>
<h4>1.6.4 Диаграммы классов </h4>
<p>Унифицированный язык моделирования (UML) предлагает графическое обозначение для класса в виде
прямоугольника, разделенного, как минимум, на три части:</p>
<p align="center"><img src="Images/03_Class.gif" width="320" height="184"></p>
<p>В приведенном примере Window – имя класса, атрибутам соответствуют поля (свойства) класса. Операциям
соответствуют методы. Можно также указать типы атрибуты, типы параметров и результата операций:</p>
<p align="center"><img src="Images/01_Class.gif" width="118" height="115"></p>
<p>Атрибуты определяют данные, описывающие экземпляр класса и определяют его состояние. В
объектно-ориентированном программировании атрибуты отображаются в поля или элементы данных. Полный
формат атрибута имеет следующий вид:</p>
<blockquote>
<pre>видимость имя : тип = значение_по_умолчанию</pre>
</blockquote>
<p>Видимость может быть следующей:</p>
<blockquote>
<pre>- закрытый (приватный)
+ открытый (публичный)
# защищенный</pre>
</blockquote>
<p>Можно использовать сокращенный формат – без видимости, без типа, без начального значения, или вообще
только имя.</p>
<p>Множественность может быть определена в квадратных скобках сразу после имени атрибута:</p>
<blockquote>
<blockquote>
<pre>coords[3]: integer
sons[0..*]: human</pre>
</blockquote>
</blockquote>
<p>Операции определяют действия, которые можно применить к классу или его объекта. Операция описывается
уровнем доступа (видимости), списком параметров и типом результата:</p>
<blockquote>
<blockquote>
<pre>видимость имя(список_параметров) : тип</pre>
</blockquote>
</blockquote>
<p>Параметры в списке отделяют друг от друга запятыми. Каждый параметр имеет следующий формат:</p>
<blockquote>
<blockquote>
<pre>направление имя : тип = значение_по_умолчанию</pre>
</blockquote>
</blockquote>
<p>Можно опустить все части спецификации операции, за исключением имени и круглых скобок.</p>
<p>Операции класса (статические) выделяются подчеркиванием.</p>
<p>UML 2 позволяет в случае необходимости добавлять четвертую часть к изображению класса. В этой части
располагают пиктограммы вложенных классов.</p>
<p><i>Ассоциации</i> – это наиболее общий тип связей между классами. С помощью ассоциаций связывают
классы, объекты которых создаются и существуют независимо. В языках программирования обыкновенная
ассоциация реализуется посредством указателей или ссылок. Ассоциация может быть направлена (один
указатель или ссылка) или направленная (экземпляры обоих классов знакомы об экземплярах противоположного
класса). Отношение типа "<i>множественность</i>" (multiplicity) показывает количество
возможных связей между экземплярами классов. Явное указание множественности можно опускать.</p>
<p align="center"><img src="Images/01_Associations.gif" width="485" height="54"></p>
<p><i>Агрегирование</i> – это специальная форма ассоциации, которая показывает, что сущность
(экземпляр) содержится в другой сущности или не может быть создана и существовать без всеохватывающей
сущности. Иногда используется более жесткая форма – композиция, которая предусматривает, что
сущность полностью содержится в другой сущности. Агрегирование и композиция позволяют указывать
множественность.</p>
<p align="center"><img src="Images/01_Aggregation.gif" width="237" height="183"></p>
<p>Отношение типа "<i>зависимость</i>" на диаграмме классов указывает, что зависимый класс
пользуется функциональностью другого класса. На уровне языка программирования это может быть реализовано
через вызов статических функций другого класса или создание временного объекта.</p>
<p align="center"><img src="Images/01_Dependency.gif" width="262" height="60"></p>
<p>В UML для представления наследования используется связь типа <em>обобщения</em> (generalization). Стрелка
специального вида ведет от более конкретного класса (производного) к более общему (базовому):</p>
<p align="center"><img src="Images/ClassesGeneralization.png" width="137" height="210"></p>
<p>Для представления полиморфизма используются абстрактные классы и операции. Их имена записываются
курсивом.</p>
<p>Для надписей на диаграммах классов можно использовать любой язык, но в тех случаях, когда диаграмма
классов используется для генерации исходного кода, следует употреблять латинские буквы и преимущественно
английскую мнемонику.</p>
<h3>1.7 Языки объектно-ориентированного программирования</h3>
<p>Первым языком программирования, в котором были предложены принципы объектной ориентированности, была
Симула, который разработали Оле-Йохан Даль и Кристен Нюгорд в Норвежском вычислительного центре. В
момент своего появления (в 1967 году), язык Симула предложил концепции объектов, классов, виртуальных
методов и др., однако все это использовалось только в контексте задач имитационного моделирования. Впоследствии эти концепции были развиты Аланом Кэйем и Дэном Ингаллсом в языке Smalltalk. Именно он стал
первым широко распространённым объектно-ориентированным языком программирования.</p>
<p>Язык программирования С++ был создан в 1983 году доктором Бьерном Страуструпом. Object Pascal появился в
1989 году, язык программирования Java был разработан в 1995 году. Существуют также C#, ADA, Oberon,
Eiffel, Ruby, Python, Visual Basic, Modula-3, Object REXX и многие другие. Объектно-ориентированные
средства присутствуют также в современных версиях PHP и JavaScript.</p>
<h3>1.8 Прототипное программирование</h3>
<p>Прототипное программирование – это вариант реализации объектно-ориентированного программирования,
при котором вместо использования классов наследование производится путем клонирования существующего
экземпляра объекта (прототипа). Каноническим примером прототип-ориентированного языка является язык
Self. В дальнейшем этот стиль программирования был положен в основу таких языков программирования, как
JavaScript, Lua, Io, REBOL и др.</p>
<p>Сторонники прототипного программирования считают, что этот подход обеспечивает лучший контроль над
объектами и связан с меньшими накладными расходами, чем традиционный объектно-ориентированный подход,
основанный на использовании классов.</p>
<h2>2 Контрольные вопросы</h2>
<ol>
<li>Что такое парадигма программирования?</li>
<li>Какие существуют парадигмы программирования?</li>
<li> В чем суть императивного программирования?</li>
<li>В чем суть структурного программирования?</li>
<li>В чем суть процедурного программирования?</li>
<li>В чем суть модульного программирования?</li>
<li>Чем обусловлено появление объектно-ориентированного подхода?</li>
<li>Чем обусловлена сложность программного обеспечения?</li>
<li>Какие основные составляющие объектно-ориентированной методологии?</li>
<li>Что такое объектно-ориентированный анализ?</li>
<li>Что такое объектно-ориентированное проектирование?</li>
<li>Что такое объектно-ориентированное программирование?</li>
<li>В чем заключается основной принцип объектно-ориентированного подхода?</li>
<li>Какие основные концепции объектно-ориентированного подхода?</li>
<li>Дайте определение класса.</li>
<li>Чем класс отличается от объекта?</li>
<li>Что такое UML?</li>
<li>Как средствами UML представить алгоритм?</li>
<li>Сколько конечных состояний может присутствовать на диаграмме деятельности?</li>
<li>Что такое диаграмма классов?</li>
<li>В чем суть инкапсуляции?</li>
<li>Каким образом инкапсуляция моделируется в UML?</li>
<li>В чем суть наследования?</li>
<li>Каким образом наследование моделируется в UML?</li>
<li>В чем суть полиморфизма?</li>
<li>В чем различие между ранним и поздним связыванием?</li>
<li>Что такое виртуальный метод?</li>
<li>Как в UML обозначается абстрактная операция?</li>
<li>В чем суть программирования, управляемого событиями?</li>
<li>Что такое прототипное программирование?</li>
</ol>
<p> </p>
<div class="w3-clear nextprev">
<a class="btn btn-info float-left" href="index.html">Предыдущая</a>
<a class="btn btn-info float-left" href="topic_1_02.html">Следующая</a>
</div>
</div>
</div>
</div>
</div>
<a href="#top" id="up">up</a>
<footer class="container-fluid text-center">
<p>© 2003-2019 Л.В.Иванов</p>
</footer>
<script>
$(document).ready(function(){
// Add smooth scrolling to all links in navbar + footer link
$("a[href='#top']").on('click', function(event) {
// Make sure this.hash has a value before overriding default behavior
if (this.hash !== "") {
// Prevent default anchor click behavior
event.preventDefault();
// Store hash
var hash = this.hash;
// Using jQuery's animate() method to add smooth page scroll
// The optional number (900) specifies the number of milliseconds it takes to scroll to the specified area
$('html, body').animate({
scrollTop: $(hash).offset().top
}, 900, function(){
// Add hash (#) to URL when done scrolling (default click behavior)
window.location.hash = hash;
});
} // End if
});
var offset = 200;
var duration = 300;
$('#up').fadeOut(0);
$(window).scroll(function() {
var winTop = $(window).scrollTop();
if (winTop > offset) {
$('#up').css("opacity", "0.8");
$('#up').fadeIn(duration);
} else {
$('#up').fadeOut(duration);
}
});
})
</script>
</body>
</html>