Лекция 14 (лекции (2002)), страница 2

2019-09-19СтудИзба

Описание файла

Файл "Лекция 14" внутри архива находится в папке "лекции (2002)". Документ из архива "лекции (2002)", который расположен в категории "". Всё это находится в предмете "языки программирования" из 7 семестр, которые можно найти в файловом архиве МГУ им. Ломоносова. Не смотря на прямую связь этого архива с МГУ им. Ломоносова, его также можно найти и в других разделах. .

Онлайн просмотр документа "Лекция 14"

Текст 2 страницы из документа "Лекция 14"

В языках C# и Java private и public применимы не только к членам классов, но и к классам вообще. В этих ЯП нет понятия глобальных функций. В Java любая программа- это совокупность определения классов. В С# к ней ещё добавляется определения, например, перечислимых ТД. В любом случае программа на этих языках- последовательность определения типов (типы: классы, интерфейсы, перечислимые типы, структуры). Никаких глобальных данных и функций. В этих ЯП в отличие от Delphi и jn C++ атрибуты private, protected и public являются атрибутами одного данного, а вовсе не переключателями. Мы должны перед каждым членом данным или функцией ставить один из этих атрибутов, или по умолчанию. Кроме этого атрибуты private и public можно ставить перед именами классов. Смысл тот же самый. Пример:

public class X {

/* public означает, что экспортируем из соответствующего пакета */

public X() { ... };

private void f() { ... }

...

};

Если напишем просто class Y { ... };- это будет по умолчанию пакетный доступ: виден в пакете (пространстве имён), но не виден извне. Похоже на реализацию. А перед всем, что относим к интерфейсу надо ставить ключевое слово public.

Мы рассмотрели вопросы связанные с инкапсуляцией данных. АТД- это ТД, у которого структура и реализация полностью закрыта от пользователя. То есть мы видим в интерфейсе только имя типа и операции. В C++, Java, C# формально АТД может называться некоторый класс у которого публичным являються только операции. Тут public могут быть только функции-члены. Мы абстрагируемся от реализации.

Во всех ООЯП существует явно или неявно понятие интерфейса, как языковое понятие- это обобщение АТД. Для этого есть соответствующее ключевое слово. В интерфейсе мы видим только опирации, либо статические члены данных (константы). Можно ли объявить класс (пусть на С++), объекты которого могут заводится только в динамической памяти и никогда не могут быть освобождены (и это контролируется компилятором). Очень просто:

class X {

public:

static X* Make() {return new X();}

/* static необходим, чтобы мы могли создать объект, иначе мы не сможем обратиться к этому методу не имея объектов данного класса */

private:

X(); /* атрибуты относятся и к специальным функциям */

~X(); /* уничтожить объект можно только в функции-члене */

};

X*p = X::Make() - единственный способ создать объект (заводится в динамической памяти)

X a; - ошибка, так как конструктор приватный

Как запретить операцию копирования объекта? (например, для класса KeyManager: класс, управляющий данными, которые должны являться уникальными ключами, тут нужен специальный алгоритм генерации плюс запрет операции копирования ). В Аде- ограниченный приватный ТД. Копирование извне запрещается так:

private:

X(X&) /* конструктор копирования (при инициализации) */

= /* операция присваивания */

Они по умолчанию генерируются публично.

Глава 7: Раздельная трансляция

Виды трансляции:

1)Пошаговая: программа разбивается на небольшие кусочки и по мере появления транслирует их (интерпритаторы с первых интерактивных ЯП [Basic: шаг- один оператор языка]; shell- работает тоже по пошаговому принцыпу).

2)Инкрементная трансляция: транслятор сам выбирает кусочки и транслирует по кусочкам- применяется для уменьшения расходов на трансляцию, даже во многих современным компиляторов с промышленных ЯП (Visual C++). Это удобно: транслируется только изменённый кусок.

3)Цельная трансляция: весь проект- это один большой кусок: несерьёзно с точки зрения промышленного подхода (например, Алгол 60). Это главный недостаток Паскаля. Все реализации стандартного Паскаля содержали нестандартные расширения языка, которые позволяли разбивать программу на большие части, которые транслировались раздельно.

4)Раздельная (независимая и зависимая): программа разбивается на отдельные физические куски (модули), которые предъявляются компилятору по кускам.

Как только мы говорим о раздельной трансляции, значит должно существовать понятие «Физический модуль»- просто кусок программы, который предъявляется на вход компилятору (может совпадать или не совпадать с логическим модулем). Эти куски иногда называют единицами компиляции (ЕК). При цельной трансляции ЕК- это целиком вся программа. Уже в Фортране (самый первый язык высокого уровня) было разбиение на модули (а именно: подпрограммы, функции, модули блоки данных, ну и главная программа), которые одновременно были и единицами компиляции.

Контекст трансляции (КТ)- в него входят имена, которые необходимы для откомпилирования единицы компиляции. Всегда ли он существует? Всегда! В него входят: совокупность имён, возможно, с их свойствами (стандартные имена и другие).

Независимая компиляции: программист сам описывает всю информацию о контексте трансляции (естественно, в языке должны существовать соответствующие конструкции для этого). Результат- объектный модуль:


obj <= транслятор <= ЕК КТ

При зависимой трансляции существует специальный механизм и транслятору на вход подаётся не только ЕК, но и соответствующий КТ, который компилятор хранит где-то отдельно. Результат: объектный модуль и добавление информации о КТ уже для данной единице:


obj <= транслятор

Существуют понятия:

1)Програмная библиотека, где хранятся все модули программы

2)Трансляционная библиотека (только информация, отражающая контекст трансляции)- чтобы можно было откомпилировать текущую единицу компиляции (для этого иметь все модули не надо, иначе у нас речь идёт о цельной трансляции).

Зависимая компиляция: зависимая, так как зависит от результата предыдущей трансляции, в отличие от независимой трансляции.

Возможность зависимой трансляции даёт значительно более богатые механизмы для проверки межмодульных связей (для проверкии соответствия типов, для проверки соответствия вызовов). При независимой трансляции мы всё это делаем вручную. Большинство современных ЯП имеют механизмы зависимой трансляции, за исключением С++.

С++: независимая трансляция, унаследованная от языка С (для совместимости). Здесь межмодульные связи приходится проверять вручную.

Самые богатые возможности по раздельной трансляции- в языке Ада. А самые простые- в языках Модула-2, Оберон и Delphi.

Как связаны понятия физического и логического модуля?

Физический модуль ≡ логический модуль (Модула-2, Оберон, Delphi):

DEFINITION MODULE M;

...

END M;

IMPLEMENTATION MODULE M;

...

END M;

- разные логические модули (интерфейс и реализация), но каждый из них одновременно является и единицей компиляции.

В програмную библиотеку входят и модуль определений и модуль реализации. Для того, чтобы система была готова к использованию надо чтобы все модули были оттранслированы, а так же, чтобы проработала программа-загрузчик для получения исполняемых файлов (одного или совокупности). В трансляционную библиотеку входят только описания модулей, потому, что язык Модула-2 сконструирован так, чтобы не зависеть от модулей реализации, с точки зрения трансляции:

модуль М:

IMPORT M1, M2. M3;

Компилятору для транслирования модуля М нужно знать все имена, которые описаны в интерфейсах М1, М2 и М3 и вся необходимая информация содержится в соответствующей трансляционной библиотеке. И если кто-то из них не оттранслирован, то компилятор выдаёт ошибку и просит перетранслировать соответствующие модули.Более того, если компилятор видит, что М1 не оттранслирован, то он перетранслирует (причём только модуль определений). Единственное исключение скрытые типы данных, именно поэтому они выглядят как указатель или тип, совместимый с указателем.

В случае языка Модула-2 совокупность модулей определений представляет собой трансляционную библиотеку, при этом конструкции IMPORT, управляющие пространством имён, при этом служат и директивами перетрансляции (для управления модулями).

Если М1 импортирует Y1, а Y1 импортирует Y2, а Y2 или Y1 импортируют модулм М:


M IMPORT M1, M2, M3;

Y1 Y2

Это ошибка логического дизайна соответствующих модулей.

С помощью совершенно тривиальных средств и механизмов зависимой трансляции, мы добиваемся того, что программист сам может управлять порядком перетрансляции модулей. Простая структура, и сильный контроль межмодульных связей, так как в модуле определений содержится вся информация.

В Обероне просто есть единый модуль:

MODULE M;

TYPE T* =

...

END M;

Но с другой стороны у нас опять же присутствует конструкция импорт и понятие интерфейса в неявном виде, благодаря этому трансляционная билблиотека (или контекст трансляции) представляет собой описание всех имён, которые экспортируются из модуля. Нет явного интерфейса, компилятор сам «вытягивает» всю эту информацию и помещает её в свою трансляционную библиотеку. Схема трансляции сходна с Модулой-2, только немного упрощена защёт отсутствия явной конструкции, которая отвечает за интерфейс. Схема Модулы-2 была выбрана такой, так как этот ЯП разрабатывался (79-80 года) для слабых по современным меркам машин, и поэтому экономии ресурсов компьютеров уделялось много внимания. Что даёт схема Модулы-2 : если поменяем только модуль реализации, все клиентские модули не нуждаются в перетрансляции (так как там вся информация для трансляции). А если мы поменяем модуль реализации, то надо перетранслировать только его. А как же в Обероне, где нет явного понятия интерфейса? Если мы что-то изменили в модуле М, должен ли компилятор перетранслировать все клиентские модули, которые прямо или косвенно импортируют этот этот модуль. Такая ситуация довольно часто возникает в языках, где интерфейс и реализация слиты воедино (В современных ЯП интерфейсы генерятся с помощью специальных утилит).

Эта же проблема возникает и в языке Delphi:

unit M;

interface

/* ... */

...

implementation

...

end M.

Тут есть понятия модуля, интерфейса и реализации.

Компилятор догадывается, когда не надо перетранслировать модули (если изменяем что-то в реализации или добавляем комментарии в интерфейс). А вот на С++ даже добавление комментариев (например, в stdio.h) приводит к перетрансляции всей программы, так как тут отсутствует как таковое понятие трансляционной библиотеки. А в этих языках оно присутствует, но неявно (каждый unit при трансляции это бинарный файл, и если его конец- это нечто очень похожее на объектный код в борландовском формате, то начало- похоже на бинарное представление некоторой таблицы имён, описанных в интерфейсе, с какими-то своими свойствами). Хотя физически- это один модуль, но компиляции результат компиляции представляет из себя две части: объектный модуль и таблици имён (как бы часть трансляционной библиотеки), и при измененияя модуля компилятор его транслирует и побайтно сравнивает их интерфейсы. Тоже самое делает и компилятор Оберона, только пользователь этого не видит, как только мы что-то изменили в интерфейсе или реализации компилятор осуществляет перетрансляцию (в Delphi, Pascal, Оберон она крайне быстра), сравнивает со старой версией и если интерфейсная часть (таблица имён, необходимая в КТ) не изменилась- значит всё хорошо и изменилась только реализация. Очень гибкое, прозрачное и простое для пользователя управление трансляцией.

Результат компиляции:


У нас есть специальные конструкции, управляющие пространством имён: IMPORT; в Turbo Pascal’e и Delphi используем конструкцию uses- эти отношения импорта очень похожи на отношение частичного порядка: M1 < M2 < M3 (“<”- импортирует), заметим, что это отношение зависимости модулей и импорт определяет некоторые зависимости этих модулей друг от друга. Если это отношение зацикливается- это уже не есть отношение частичного порядка. С помощью импорт мы задаём лишь частичный порядок. Задача траслятора: перевести частичный порядок в линейный. Компилятор в начале находит модули ни от кого не зависящие (листевые), далее модули от которых зависят вот эти, и так далее. Это линейка модулей- это не только управление порядком перетрансляции, но и более интересный вопрос: в каком порядке модули загружаются в память? Вначале модули, которые не от кого не зависят, далее модули, которые зависят только от независимых и так далее, последней в память будет загружена головная программа, которая зависит от всех, а от неё никто не зависит. В процессе загрузки естественно выполняется и инициализация. Многие проблеммы (например, как мы уже говорили, в С++ программист не мог управлять порядком выполнения конструкторов статических объектов) решаются благодаря раздельной зависимой трансляции.

Более нетривиальные случаи:

Ада: механизм раздельной трансляции доведён до совершенства. Для упрощения, во всех языках, которые мы разбирали физический модуль совпадает с логическим. В Аде сделано хитрее. Тут сказано, что вопрос раздельной трансляцияии- это проблемма программиста: он сам решает, какие логические модули делать единицами компиляции, а какие нет. Есть возможность несколько логических модулей объединить в одну единицу компиляции. И правила раздельной трансляции в языке Ада сконструированы таким образом, чтобы эффект раздельной трансляции не зависел от того, как программа разбита на модули.

Пусть в программе три пакета: М1, М2 и М3. Их можно транслировать раздельно, а можно и все вместе, сделав компиляцию цельной. А эффект должен быть одним и тем же (один и тот же объектный код). Так же, вспомним, что сама по себе модульная структура языка Ада более сложная, чем те, о которых мы говорили. Тут модули могут вкладываться друг в друга сколько угодно. В Аде возможности раздельной трансляции распространяются на произвольные модули: вложенные, отдельно стоящие и так далее.

В Аде ЕК ≠ логическому модулю (спецификация пакета, тело пакета, подпрограммы). Во всех языках, где есть глобальные подпрограммы (процедуры и функции) они тоже являются логическими модулями. Так вот, в принцыпе, каждый из этих логических модулей может стать единицей компиляции. Тогда возникает вопрос: каким образом управлять контекстом? Для управления контекстом служат два вида связывания (для связывания в одну программу транслированных модулей:

а)Одностороннее(было в Модуле-2, Обероне и Delphi)- клиентский модуль знает о сервисном, а сервисный ничего не знает о клиентском: М1 < М2 отношение связывания- несимметричное отношение, то есть если модуль М1 импортирует данные из модуля М2, это означает, что он с ним связан. Но знает ли что-то модуль М2 о модуле М1? Ответ: ничего! Сервисные модули ничего не знают о своих клиентах, а клиенты знают, потому, что именно они указывают имена сервисных модулей. Это характерно для стиля программирования снизу-вверх. Так же мы отметили, что есть стиль программирования сверху вниз. И, если язык поддерживает технологию сверху-вниз, он, по идее, должен содержать конструкции, которые позволяют одни модули объявлять в контексте других. И мы говорили, что в некоторых случаях это очень полезно:


Свежие статьи
Популярно сейчас
Почему делать на заказ в разы дороже, чем купить готовую учебную работу на СтудИзбе? Наши учебные работы продаются каждый год, тогда как большинство заказов выполняются с нуля. Найдите подходящий учебный материал на СтудИзбе!
Ответы на популярные вопросы
Да! Наши авторы собирают и выкладывают те работы, которые сдаются в Вашем учебном заведении ежегодно и уже проверены преподавателями.
Да! У нас любой человек может выложить любую учебную работу и зарабатывать на её продажах! Но каждый учебный материал публикуется только после тщательной проверки администрацией.
Вернём деньги! А если быть более точными, то автору даётся немного времени на исправление, а если не исправит или выйдет время, то вернём деньги в полном объёме!
Да! На равне с готовыми студенческими работами у нас продаются услуги. Цены на услуги видны сразу, то есть Вам нужно только указать параметры и сразу можно оплачивать.
Отзывы студентов
Ставлю 10/10
Все нравится, очень удобный сайт, помогает в учебе. Кроме этого, можно заработать самому, выставляя готовые учебные материалы на продажу здесь. Рейтинги и отзывы на преподавателей очень помогают сориентироваться в начале нового семестра. Спасибо за такую функцию. Ставлю максимальную оценку.
Лучшая платформа для успешной сдачи сессии
Познакомился со СтудИзбой благодаря своему другу, очень нравится интерфейс, количество доступных файлов, цена, в общем, все прекрасно. Даже сам продаю какие-то свои работы.
Студизба ван лав ❤
Очень офигенный сайт для студентов. Много полезных учебных материалов. Пользуюсь студизбой с октября 2021 года. Серьёзных нареканий нет. Хотелось бы, что бы ввели подписочную модель и сделали материалы дешевле 300 рублей в рамках подписки бесплатными.
Отличный сайт
Лично меня всё устраивает - и покупка, и продажа; и цены, и возможность предпросмотра куска файла, и обилие бесплатных файлов (в подборках по авторам, читай, ВУЗам и факультетам). Есть определённые баги, но всё решаемо, да и администраторы реагируют в течение суток.
Маленький отзыв о большом помощнике!
Студизба спасает в те моменты, когда сроки горят, а работ накопилось достаточно. Довольно удобный сайт с простой навигацией и огромным количеством материалов.
Студ. Изба как крупнейший сборник работ для студентов
Тут дофига бывает всего полезного. Печально, что бывают предметы по которым даже одного бесплатного решения нет, но это скорее вопрос к студентам. В остальном всё здорово.
Спасательный островок
Если уже не успеваешь разобраться или застрял на каком-то задание поможет тебе быстро и недорого решить твою проблему.
Всё и так отлично
Всё очень удобно. Особенно круто, что есть система бонусов и можно выводить остатки денег. Очень много качественных бесплатных файлов.
Отзыв о системе "Студизба"
Отличная платформа для распространения работ, востребованных студентами. Хорошо налаженная и качественная работа сайта, огромная база заданий и аудитория.
Отличный помощник
Отличный сайт с кучей полезных файлов, позволяющий найти много методичек / учебников / отзывов о вузах и преподователях.
Отлично помогает студентам в любой момент для решения трудных и незамедлительных задач
Хотелось бы больше конкретной информации о преподавателях. А так в принципе хороший сайт, всегда им пользуюсь и ни разу не было желания прекратить. Хороший сайт для помощи студентам, удобный и приятный интерфейс. Из недостатков можно выделить только отсутствия небольшого количества файлов.
Спасибо за шикарный сайт
Великолепный сайт на котором студент за не большие деньги может найти помощь с дз, проектами курсовыми, лабораторными, а также узнать отзывы на преподавателей и бесплатно скачать пособия.
Популярные преподаватели
Добавляйте материалы
и зарабатывайте!
Продажи идут автоматически
5301
Авторов
на СтудИзбе
417
Средний доход
с одного платного файла
Обучение Подробнее