0
votes

The function excludes produces all of the characters in str that are not upper case or lower case letters or the numbers 0-9. If the string is empty it produces " ".

Code

(define (alphanum? c)
  (or (char-numeric? c)
      (char-alphabetic? c)))


example: (excludes " " ) => " " (excludes "@hello friend#!")=>"@#!" in that order How would I do this without using abstract functions such as filter etc.

2

2 Answers

1
votes
; String [Char -> Boolean] -> String
; filters string's characters by fun
(define (filter-string-by str fun)
  (list->string (filter fun (string->list str))))

; Char -> Boolean
; is char alphanumeric?
(define (alphanum? char)
  (or (char-alphabetic? char)
      (char-numeric? char)))

; String -> String
; only include alphanum chars in the str
(define (only-include-alphanum str)
  (filter-string-by str alphanum?))

Custom filter

; [X] [X -> Boolean] [List-of X] -> [List-of X]
; keeps each element, e, of l where (f e) holds
(define (my-filter f l)
  (cond
    [(empty? l) '()]
    [else (if (f (first l))
              (cons (first l) (my-filter f (rest l)))
              (my-filter f (rest l)))]))
1
votes

The "trick" here is to convert the string to a list and back so you can use list functions and recurse conveniently.

Without using any higher-order functions like filter, the basic filtering recursion over a list looks a bit like this:

(define (a-filter ls)
    (cond [(null? ls) '()]
          [(include? (car ls)) (cons (car ls) (a-filter (cdr ls)))]
          [else (a-filter (cdr ls))]))

where the procedure include? is entirely fictional.

In your case, you could write this:

(define (no-alphanums ls)
    (cond ((null? ls) '())
          ((not (alphanum? (car ls))) (cons (car ls) (no-alphanums (cdr ls))))
          (else (no-alphanums (cdr ls)))))

and then you can define

(define (excludes s) 
    (list->string (no-alphanums (string->list s))))