#list #scheme #median
#Список #схема #медиана
Вопрос:
Программа, которую я пытаюсь создать, — это программа, которая может выполнять ряд математических функций от average до std-dev и так далее, но та, на которой я спотыкаюсь, — это median. Список уже отсортирован, так как я могу получить длину этого списка, чтобы определить, четный или нечетный, а затем получить медиану из этого. Текущий код ниже. Довольно новичок в схеме, поэтому синтаксис меня все еще сбивает с толку.
код
(define make-tswb
(lambda ()
(let ((records '()))
(lambda (command . args)
(cond
((equal? command 'empty?)
(null? records))
((equal? command 'add!)
(set! records (cons (car args) records)))
((equal? command 'get)
(letrec ((sort-records (lambda (r) (sort r (lambda (x y) (<= (car x) (car y)))))))
(if (null? args)
(sort-records records)
(sort-records (filter(car args) records)))))
((equal? command 'analytic)
(cond
((= (length args) 1)
((car args) records))
((= (length args) 2)
((car args) (filter (cadr args) records))))))))))
(define listofVal
(lambda (lst)
(if (null? lst)
'()
(sort (map cadddr lst) <))))
(define median
(lambda (medianList)
(let ((values (listofVal medianList)))
(let ((len (length medianList)))
// ??????????
(define tswb (make-tswb))
(tswb 'add! '(2 123 "temp1" 76.1))
(tswb 'add! '(1 123 "temp1" 72.0))
(tswb 'add! '(1 123 "temp1" 75.0))
(tswb 'analytic median)
Ответ №1:
Согласно этой странице, вам необходимо обработать два случая:
- Длина списка — четное число.
- Это не четное число.
Для первого случая вам нужно взять два значения в середине, посчитать их сумму, а затем разделить на два. Во втором случае вам нужно найти середину отсортированного списка, и это значение будет медианой.
Итак, я думаю, это должно сработать для вас:
(define (count-median-for-even len listOfVal)
(/ ( (list-ref listOfVal (round (- (/ len 2) 1)))
(list-ref listOfVal (round (/ len 2)))) 2))
(define (count-median-for-odd len listOfVal)
(list-ref listOfVal (round (/ len 2))))
(define median
(lambda (medianList)
(let ((values (listofVal medianList)))
(let ((len (length medianList)))
(if (even? len) (count-median-for-even len values) (count-median-for-odd len values))))))
Протестировав это на трех тестовых примерах по ссылке выше, я могу сказать, что это должно сделать работу за вас.