Является ли стандартным для интерпретаторов Scheme запрет на использование операторов if без альтернативных предложений? - PullRequest
2 голосов
/ 15 мая 2019

Я новичок в Scheme, и у меня есть фоновое кодирование, в основном на C ++ / Java, и немного Python.Я делаю упражнения в «Изучении и интерпретации компьютерных программ», и я столкнулся с этой проблемой:

В книге подробно описывается структура специальной формы «if» как (if (условная) (последующее предложение)(альтернативный пункт)).Однако ничто не указывает на то, что альтернативное предложение ДОЛЖНО быть включено.

Фактически, в упражнении, в котором я сейчас занят (упражнение 1.22, для всех, кто интересуется), они предоставляют некоторый код, который мы должны использовать при создании процедуры, которая проверяет простые числа в заданном диапазоне.и дает количество времени, необходимое для их поиска.

(define (start-prime-test n start-time)
    (if (is-prime n)
        (report-prime (- (runtime) start-time))))

Это не сработало, поэтому я немного его изменил:

(define (start-prime-test n start-time)
    (if (is-prime n)
        (report-prime (- (runtime) start-time))
        (display ""))) ;prints nothing

Первая версия приводит к "SchemeError: слишком малооперанды ... "Я изменил это, чтобы иметь альтернативное предложение, которое по существу ничего не делает, и я больше не получаю ошибку при тестировании процедуры.

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

Любая помощь будет принята с благодарностью;Мне не нравится включать процедуры "ничего не делать".

Ответы [ 3 ]

2 голосов
/ 15 мая 2019

В большинстве интерпретаторов Scheme if допускает выражения без части "else", и это то, что говорит стандарт , как указывает @codybartfast в своем ответе.

Мне известно только о том, что Racket применяет правило, согласно которому if всегда должно иметь как последующую, так и альтернативную части, и это по очень веской причине: это поможет вам уловить ошибки, которые случаются, когда вы забываете написать часть "еще".

Хотя допустимо иметь if выражений без альтернативной части, это происходит только тогда, когда мы пишем процедурный код (например, отображение результата в вашем примере), и именно такой стиль программирования мы хотим избегать при использовании Scheme (поскольку мы предпочитаем функциональное программирование).

Сказав, что, если вы абсолютно уверены, что хотите написать процедурный код, то вам следует использовать when, который не имеет части else и в отличие от if, он может иметь несколько выражений внутри, потому что у него есть неявное begin. Это будет работать:

(define (start-prime-test n start-time)
  (when (is-prime n)
    (report-prime (- (runtime) start-time))))
1 голос
/ 15 мая 2019

Я понимаю, что R5RS / R6RS фактически являются языковыми стандартами.Они говорят, что альтернативное предложение является необязательным :

(if <test> <consequent> <alternate>)‌‌syntax  
(if <test> <consequent>)‌‌syntax  

Syntax: <Test>, <consequent>, and <alternate> must be expressions.

Semantics: An if expression is evaluated as follows: first, <test> is
evaluated. If it yields a true value (see section 5.7), then <consequent> is
evaluated and its values are returned. Otherwise <alternate> is evaluated
and its values are returned. If <test> yields #f and no <alternate> is
specified, then the result of the expression is unspecified.

Но в 2009 году (совсем недавно для схемы) комитет по управлению языками сказал :

Увы: у Схемы есть печальное различие, что она является самым непереносимым языком программирования в мире.Это почти вводит в заблуждение называть Scheme «языком программирования»;было бы точнее охарактеризовать Scheme как семейство диалектов, все они слабо связаны общими чертами лексического контекста, динамической типизации, структурой списков, функциями высшего порядка, правильной хвостовой рекурсией, сборкой мусора, макросами и (некоторые формыиз) лексический синтаксис, основанный на s-выражениях.

Таким образом, хотя формальный стандарт может существовать, вряд ли можно ожидать, что любая данная реализация будет придерживаться этого стандарта.Например, по умолчанию для Racket требуется альтернативное предложение.(Хотя Racket также может поддерживать совместимый с R6RS набор.)

Лично я использую Racket с языковым пакетом SICP , чтобы соответствовать книге.

0 голосов
/ 15 мая 2019

Однорукий if действительно был стандартом в Схеме некоторое время.

К сожалению, однорукий if позволяет ошибиться - забыть о второй руке очень легко.,Некоторые реализации добавили when и unless для уменьшения количества ошибок.

См. Также: Почему однорукое "если" отсутствует в Racket?

...