|
||||
Меню:
Главная
Форум
Литература: Программирование и ремонт Импульсные блоки питания Неисправности и замена Радиоэлектронная аппаратура Микросхема в ТА Рубрикатор ТА Кабельные линии Обмотки и изоляция Радиоаппаратура Гибкие диски часть 2 часть 3 часть 4 часть 5 Ремонт компьютера часть 2 Аналитика: Монтаж Справочник Электроника Мощные высокочастотные транзисторы 200 микросхем Полупроводники ч.1 Часть 2 Алгоритмические проблемы 500 микросхем 500 микросхем Сортировка и поиск Монады Передача сигнала Электроника Прием сигнала Телевидиние Проектирование Эвм Оптимизация Автомобильная электроника Поляковтрансиверы Форт Тензодатчик Силовые полевые транзисторы Распределение частот Резисторные и термопарные Оберон Открытые системы шифрования Удк |
[142] Процедуры stream-append-delayed и interleave-delayed подобны stream-append и interleave (раздел 3.5.3), но только они принимают задержанный аргумент (как процедура integral из раздела 3.5.4). В некоторых случаях это откладывает зацикливание (см. упражнение 4.71). (define (stream-append-delayed si delayed-s2) (if (stream-null? si) (force delayed-s2) (cons-stream (stream-car si) (stream-append-delayed (stream-cdr si) delayed-s2)))) (define (interleave-delayed si delayed-s2) (if (stream-null? si) (force delayed-s2) (cons-stream (stream-car si) (interleave-delayed (force delayed-s2) (delay (stream-cdr si)))))) Процедура stream-flatmap, которая многократно используется в интерпретаторе, чтобы применить процедуру ко всем элементам потока кадров и соединить получающиеся потоки кадров, является потоковым аналогом процедуры flatmap для обычных списков, введенной в разделе 2.2.3. Однако, в отличие от обычного flatmap, потоки мы собираем с помощью чередующего процесса, а не просто сцепляем их (см. упражнения 4.72 и 4.73). (define (stream-flatmap proc s) (flatten-stream (stream-map proc s))) (define (flatten-stream stream) (if (stream-null? stream) the-empty-stream (interleave-delayed (stream-car stream) (delay (flatten-stream (stream-cdr stream)))))) Кроме того, интерпретатор пользуется следующей простой процедурой для порождения потока, который состоит из одного элемента: (define (singleton-stream x) (cons-stream x the-empty-stream)) 4.4.4.7 Процедуры, определяющие синтаксис запросов Процедуры type и contents, используемые в qeval (раздел 4.4.4.2), указывают, что особая форма определяется символом в ее car. Это те же процедуры, что type-tag и contents из раздела 2.4.2, с точностью до сообщения об ошибке. (define (type exp) (if (pair? exp) (car exp) (error "Неизвестное выражение TYPE" exp))) (define (contents exp) (if (pair? exp) (cdr exp) (error "Неизвестное выражение CONTENTS" exp))) Следующие процедуры, вызываемые из query-driver-loop (раздел 4.4.4.1), указывают, что утверждения и правила добавляются в базу данных при помощи выражений вида (assert! (правило-или-утверждение)): (define (assertion-to-be-added? exp) (eq? (type exp) assert!)) (define (add-assertion-body exp) (car (contents exp))) Вот синтаксические определения для особых форм and, or, not и lisp-value (раздел 4.4.4.2): (define (empty-conjunction? exps) (null? exps)) (define (first-conjunct exps) (car exps)) (define (rest-conjuncts exps) (cdr exps)) (define (empty-disjunction? exps) (null? exps)) (define (first-disjunct exps) (car exps)) (define (rest-disjuncts exps) (cdr exps)) (define (negated-query exps) (car exps)) (define (predicate exps) (car exps)) (define (args exps) (cdr exps)) Следующие три процедуры определяют синтаксис правил: (define (rule? statement) (tagged-list? statement rule)) (define (conclusion rule) (cadr rule)) (define (rule-body rule) (if (null? (cddr rule)) (always-true) (caddr rule))) Query-driver-loop (раздел 4.4.4.1) вызывает query-syntax-process, чтобы преобразовать переменные образца в выражении, имеющие форму ?sym-bol, к внутреннему формату (? symbol) . Это означает, что образец вроде (должность ?x ?y) на самом деле представляется внутри системы как (должность (? x) (? y)). Это повышает эффективность обработки запросов, потому что позволяет системе проверять, является ли выражение переменной, путем проверки car (не является ли car символом ?), вместо того, чтобы извлекать из символа буквы. Преобразование синтаксиса осуществляется следующей процедурой: ° 81 Большинство Лисп-систем позволяет пользователю изменять обыкновенную процедуру read и осуществлять такие преобразования путем определения макросимволов ввода (reader macro (define (query-syntax-process exp) (map-over-symbols expand-question-mark exp)) (define (map-over-symbols proc exp) (cond ((pair? exp) (cons (map-over-symbols proc (car exp)) (map-over-symbols proc (cdr exp)))) ((symbol? exp) (proc exp)) (else exp))) (define (expand-question-mark symbol) (let ((chars (symbol->string symbol))) (if (string=? (substring chars 0 1) "?") (list ? (string->symbol (substring chars i (string-length chars)))) symbol))) После того, как переменные таким образом преобразованы, переменные в образцах - это списки, начинающиеся с ?, а константные символы (которые требуется распознавать для индексирования базы данных, раздел 4.4.4.5) - это просто символы. (define (var? exp) (tagged-list? exp ?)) (define (constant-symbol? exp) (symbol? exp)) Во время применения правил при помощи следующих процедур порождаются уникальные переменные (раздел 4.4.4.4). Уникальным идентификатором правила служит число, которое увеличивается при каждом применении правила: (define rule-counter 0) (define (new-rule-application-id) (set! rule-counter (+ 1 rule-counter)) rule-counter) (define (make-new-variable var rule-application-id) (cons ? (cons rule-application-id (cdr var)))) Когда query-driver-loop конкретизирует запрос для печати ответа, она преобразует все несвязанные переменные запроса обратно к печатной форме при помощи (define (contract-question-mark variable) (string->symbol characters). Закавыченные выражения уже обрабатываются таким образом: процедура чтения автоматически переводит expression в (quote expression), прежде чем выражение видит интерпретатор. Можно было бы устроить преобразование ?expression в (? expression) таким же образом; однако ради большей ясности мы здесь представили процедуру преобразования явно. Expand-question-mark и contract-question-mark используют несколько процедур, имя которых содержит string. Это примитивы языка Scheme. |
Среды: Smalltalk80 MicroCap Local bus Bios Pci 12С ML Микроконтроллеры: Atmel Intel Holtek AVR MSP430 Microchip Книги: Емкостный датчик 500 схем для радиолюбителей часть 2 (4) Структура компьютерных программ Автоматическая коммутация Кондиционирование и вентиляция Ошибки при монтаже Схемы звуковоспроизведения Дроссели для питания Блоки питания Детекторы перемещения Теория электропривода Адаптивное управление Измерение параметров Печатная плата pcad pcb Физика цвета Управлении софтверными проектами Математический аппарат Битовые строки Микроконтроллер nios Команды управления выполнением программы Перехода от ahdl к vhdl Холодный спай Усилители hi-fi Электронные часы Сердечники из распылённого железа Анализ алгоритмов 8-разрядные КМОП Классификация МПК История Устройства автоматики Системы и сети Частотность Справочник микросхем Вторичного электропитания Типы видеомониторов Радиобиблиотека Электронные системы Бесконтекстный язык Управление техническими системами Монтаж печатных плат Работа с коммуникациями Создание библиотечного компонента Нейрокомпьютерная техника Parser Пи-регулятор ч.1 ПИ-регулятор ч.2 Обработка списков Интегральные схемы Шина ISAВ Шина PCI Прикладная криптография Нетематическое: Взрывной автогидролиз Нечеткая логика Бытовые установки (укр) Автоматизация проектирования Сбор и защита Дискретная математика Kb радиостанция Энергетика Ретро: Прием в автомобиле Управление шаговым двигателем Магнитная запись Ремонт микроволновки Дискретные системы часть 2 | ||