2017-01-03 14 views
0

Я хочу получить две строки в качестве аргументов и проверить, является ли первая строка началом второй строки. Я не могу получить это, так как не знаю, как получить строки в качестве аргументов для моей функции.Строки как аргумент функции Scheme Racket

(define starts-with(lambda (prefix str) 
        (define str2 (string->list (str))) 
        (define prefix2 (string->list (prefix))) 
(cond ((= (string-length(prefix2) 0) display "#t") 
     ((= car(prefix2) car(str2)) (starts-with (cdr(prefix2)cdr(str2)))) 
     (display "#f"))))) 

Error: application: not a procedure; expected a procedure that can be 
applied to arguments 

Дано: «аб» аргументы ...: [никто]

Может кто-нибудь объяснить мне, что это моя ошибка, и в целом, как схема работает со списками или строк ..? Я хочу иметь:

(starts-with "baz" "bazinga!") ;; "#t" 

ответ

1

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

(define (starts-with prefix str) 
    (let loop ((prefix2 (string->list prefix)) ; convert strings to char lists 
      (str2 (string->list str)))  ; but do it only once at start 
    (cond ((null? prefix2) #t) ; if the prefix is empty, we're done 
      ((null? str2) #f) ; if the string is empty, then it's #f 
      ((equal? (car prefix2) (car str2)) ; if the chars are equal 
      (loop (cdr prefix2) (cdr str2))) ; then keep iterating 
      (else #f))))      ; otherwise it's #f 

Будьте в курсе следующих ошибок в исходной реализации:

  • Вы должны преобразовать строки в списки символов, но только один раз перед тем, как начать с рекурсии.
  • Потому что мы будем нуждаться в процедуре помощника, это хорошая идея использовать именованный let для него - это просто синтаксический сахар для рекурсивной процедуры, на самом деле не петля
  • Вы отсутствовали случай, когда строка короче, чем префикс
  • вы не должны display значения, которые вы собираетесь вернуться, просто вернуть их
  • Мы не должны использовать = для сравнения символов, правильный способ заключается в использовании char=? или equal?, который является более общим
  • Последнее условие cond должен быть else
  • И последнее, но не менее, иметь в виду, что на схеме функция вызывается так: (f x) и не так: f(x). Кроме того, вы не можете положить () вокруг чего-то если вы не намерены называть его как функцию, поэтому это: (str) производила ошибку application: not a procedure; expected a procedure that can be applied to arguments
+0

Lopez первое спасибо, второй - «список prefix2 (string-> prefix) '- эта строка будет выполняться только один раз или каждый шаг рекурсии? – mooly

+1

@mooly В моем коде он будет выполнен только один раз; в вашем коде он выполнялся каждый раз - и он вызывает ошибку, потому что второй раз параметр уже является списком символов, а не строкой. –