Главная » Просмотр файлов » Х. Абельсон, Дж. Дж. Сассман, Дж. Сассман - Структура и интерпретация компьютерных программ

Х. Абельсон, Дж. Дж. Сассман, Дж. Сассман - Структура и интерпретация компьютерных программ (1108516), страница 64

Файл №1108516 Х. Абельсон, Дж. Дж. Сассман, Дж. Сассман - Структура и интерпретация компьютерных программ (Х. Абельсон, Дж. Дж. Сассман, Дж. Сассман - Структура и интерпретация компьютерных программ) 64 страницаХ. Абельсон, Дж. Дж. Сассман, Дж. Сассман - Структура и интерпретация компьютерных программ (1108516) страница 642019-04-28СтудИзба
Просмтор этого файла доступен только зарегистрированным пользователям. Но у нас супер быстрая регистрация: достаточно только электронной почты!

Текст из файла (страница 64)

Он устанавливает свой вывод product в 0,если хотя бы один множитель равен 0, даже в том случае, когда второй множительнеизвестен.(define (multiplier m1 m2 product)(define (process-new-value)(cond ((or (and (has-value? m1) (= (get-value m1) 0))(and (has-value? m2) (= (get-value m2) 0)))(set-value! product 0 me))((and (has-value? m1) (has-value? m2))(set-value! product(* (get-value m1) (get-value m2))me))((and (has-value? product) (has-value? m1))(set-value! m2(/ (get-value product) (get-value m1))me))3.3. Моделирование при помощи изменяемых данных277((and (has-value? product) (has-value? m2))(set-value! m1(/ (get-value product) (get-value m2))me))))(define (process-forget-value)(forget-value! product me)(forget-value! m1 me)(forget-value! m2 me)(process-new-value))(define (me request)(cond ((eq? request ’I-have-a-value)(process-new-value))((eq? request ’I-lost-my-value)(process-forget-value))(else(error "Неизвестный запрос -- MULTIPLIER" request))))(connect m1 me)(connect m2 me)(connect product me)me)Конструктор constant просто устанавливает значение указанного соединителя.

Сообщение I-have-a-value либо I-lost-my-value, посланные блоку-константе, приводят к ошибке.(define (constant value connector)(define (me request)(error "Неизвестный запрос -- CONSTANT" request))(connect connector me)(set-value! connector value me)me)Наконец, тестер печатает сообщение о присваивании или потере значения в указанномсоединителе:(define (probe name connector)(define (print-probe value)(newline)(display "Тестер: ")(display name)(display " = ")(display value))(define (process-new-value)(print-probe (get-value connector)))(define (process-forget-value)(print-probe "?"))(define (me request)(cond ((eq? request ’I-have-a-value)(process-new-value))((eq? request ’I-lost-my-value)278Глава 3.

Модульность, объекты и состояние(process-forget-value))(else(error "Неизвестный запрос -- PROBE" request))))(connect connector me)me)Представление соединителейСоединитель представляется в виде процедурного объекта с внутренними переменными состояния: value, значение соединителя; informant, объект, который установилзначение соединителя; и constraints, множество ограничений, в которых участвуетсоединитель.(define (make-connector)(let ((value false) (informant false) (constraints ’()))(define (set-my-value newval setter)(cond ((not (has-value? me))(set! value newval)(set! informant setter)(for-each-except setterinform-about-valueconstraints))((not (= value newval))(error "Противоречие" (list value newval)))(else ’ignored)))(define (forget-my-value retractor)(if (eq? retractor informant)(begin (set! informant false)(for-each-except retractorinform-about-no-valueconstraints))’ignored))(define (connect new-constraint)(if (not (memq new-constraint constraints))(set! constraints(cons new-constraint constraints)))(if (has-value? me)(inform-about-value new-constraint))’done)(define (me request)(cond ((eq? request ’has-value?)(if informant true false))((eq? request ’value) value)((eq? request ’set-value!) set-my-value)((eq? request ’forget) forget-my-value)((eq? request ’connect) connect)(else (error "Неизвестная операция -- CONNECTOR"request))))me))3.3.

Моделирование при помощи изменяемых данных279Внутренняя процедура соединителя set-my-value зовется, когда поступает требование установить значение соединителя. Если у соединителя нет текущего значения, онего устанавливает и запоминает ограничение, которое потребовало установки значения,в переменной informant32 .

Затем соединитель оповещает все связанные с ним ограничения, кроме того, которое потребовало установить значение. Это проделывается спомощью следующего итератора, который применяет указанную процедуру ко всем элементам списка, кроме одного.(define (for-each-except exception procedure list)(define (loop items)(cond ((null? items) ’done)((eq? (car items) exception) (loop (cdr items)))(else (procedure (car items))(loop (cdr items)))))(loop list))Если от соединителя требуют забыть значение, он запускает внутреннюю процедуру forget-my-value, которая первым делом убеждается, что запрос исходит от тогоже самого объекта, который значение установил.

Если это так, соединитель оповещаетсвязанные с ним ограничения о потере значения.Внутренняя процедура connect добавляет указанное ограничение к списку ограничений, если его там еще нет. Затем, если у соединителя есть значение, он сообщает обэтом ограничению.Процедура соединителя me служит диспетчером для остальных внутренних процедур,а кроме того, представляет соединитель как объект. Следующие процедуры предоставляют синтаксический интерфейс к диспетчеру:(define (has-value? connector)(connector ’has-value?))(define (get-value connector)(connector ’value))(define (set-value! connector new-value informant)((connector ’set-value!) new-value informant))(define (forget-value! connector retractor)((connector ’forget) retractor))(define (connect connector new-constraint)((connector ’connect) new-constraint))Упражнение 3.33.С помощью элементарных ограничений сумматор, умножитель и константа, определите процедуруaverager (усреднитель), которая принимает три соединителя a, b и c, и обеспечивает условие,что значение c равно среднему арифметическому значений a и b.32 Setter может и не быть ограничением.

В примере с температурой мы использовали символ user вкачестве значения setter.280Глава 3. Модульность, объекты и состояниеУпражнение 3.34.Хьюго Дум хочет построить квадратор, блок-ограничение с двумя выводами, такое, что значениесоединителя b на втором выводе всегда будет равно квадрату значения соединителя a на первомвыводе. Он предлагает следующее простое устройство на основе умножителя:(define (squarer a b)(multiplier a a b))В такой идее есть существенная ошибка. Объясните ее.Упражнение 3.35.Бен Битобор объясняет Хьюго, что один из способов избежать неприятностей в упражнении 3.34— определить квадратор как новое элементарное ограничение. Заполните недостающие части вБеновой схеме процедуры, реализующей такое ограничение:(define (squarer a b)(define (process-new-value)(if (has-value? b)(if (< (get-value b) 0)(error "квадрат меньше 0 -- SQUARER" (get-value b))hальтернатива1i)hальтернатива2i))(define (process-forget-value) hтело1i)(define (me request) hтело2i)hостаток определенияime)Упражнение 3.36.Допустим, что мы выполняем следующую последовательность действий в глобальном окружении:(define a (make-connector))(define b (make-connector))(set-value! a 10 ’user)В какой-то момент при вычислении set-value! будет выполнено следующее выражение из внутренней процедуры соединителя:(for-each-except setter inform-about-value constraints)Нарисуйте диаграмму, изображающую окружение, в котором выполняется указанное выражение.Упражнение 3.37.Процедура celsius-fahrenheit-converter выглядит громоздко по сравнению со стилемопределения в формате выражения:(define (celsius-fahrenheit-converter x)(c+ (c* (c/ (cv 9) (cv 5))x)(cv 32)))(define C (make-connector))(define F (celsius-fahrenheit-converter C))3.4.

Параллелизм: время имеет значение281Здесь c+, c* и т. п. — «ограничительные» версии арифметических операций. Например, c+берет в виде аргументов два соединителя, и возвращает соединитель, который связан с нимиограничением-сумматором:(define (c+ x y)(let ((z (make-connector)))(adder x y z)z))Определите аналогичные процедуры для c-, c*, c/ и cv (константа), так, чтобы можно былоопределять составные ограничения, как в вышеприведенном примере33.3.4.

Параллелизм: время имеет значениеМы убедились в мощности вычислительных объектов с внутренним состоянием вкачестве инструмента моделирования. Однако, как было сказано в разделе 3.1.3, за этумощность приходится платить потерей референциальной прозрачности, которая ведет вдебри вопросов об идентичности и изменении, и необходимостью замены подстановочноймодели вычислений на более сложную модель с окружениями.Главная проблема, стоящая за сложностями состояния, идентичности и изменения,состоит в том, что, введя присваивание, мы вынуждены внести в свои вычислительныемодели понятие времени (time).

До того, как появилось присваивание, наши программыот времени не зависели — в том смысле, что всякое выражение, обладающее значением,всегда имело одно и то же значение. Вспомним, однако, пример со снятием денег сосчета и просмотром получившегося баланса из начала раздела 3.1.1:33 Представление в виде выражений удобно, потому что при этом отпадает необходимость давать именапромежуточным выражениям в вычислении. Наша исходная формулировка языка ограничений громоздка потой же причине, по которой многие языки оказываются громоздкими при работе с составными данными.Например, если нам нужно вычислить произведение (a + b) · (c + d), где переменные представляют вектора, мыможем работать в «императивном» стиле, с процедурами, которые присваивают значения указанным векторнымаргументам, но сами не возвращают вектора как значения:(v-sum a b temp1)(v-sum c d temp2)(v-prod temp1 temp2 answer)С другой стороны, мы можем работать с выражениями, используя процедуры, которые возвращают векторакак значения, и таким образом избежать прямого упоминания temp1 и temp2:(define answer (v-prod (v-sum a b) (v-sum c d)))Поскольку Лисп позволяет возвращать составные объекты как результаты процедур, мы можем преобразовать свой императивный язык ограничений в язык на основе выражений, как показано в этом упражнении.В языках, где средства работы с составными объектами бедны, как в Алголе, Бейсике и Паскале (если явноне использовать паскалевские переменные-указатели), обычно при решении таких задач программист ограничен императивным стилем.

Характеристики

Список файлов книги

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