#functional-programming #scheme
#функциональное программирование #схема
Вопрос:
Я пытаюсь найти длину списка, используя Map / Foldl / Foldr
(define (suml lst)
(length lst))
Input : (suml '(1 2 3))
Output : 3
Input : (suml '(((((2)))) (1)))
Output: 2
Как я могу изменить его работу с foldl / map / foldr?
Комментарии:
1. Вы не можете найти длину списка с помощью,
map
потому чтоmap
функция применяется к каждому элементу списка, но знание длины требует наличия информации о всем списке. Однако ваш код немного глуповат, посколькуlength
это уже функция, которая получает длину списка. Просто отбросьтеmap
и используйте(length lst)
(и в этот момент вы можете отброситьsuml
оболочку, так как это простоlength
). Или вы на самом деле пытаетесь сделать что-то еще?2. Как должна работать функция. Можете ли вы привести пример ввода и ожидаемый результат?
3. Я обновил OP, пожалуйста, проверьте 🙂 Сильвестр Алексис Кинг
Ответ №1:
Как уже упоминалось в комментариях, карта принимает функцию и применяет ее поэлементно. Функция, использующая карту, создаст список той же длины. Чтобы создать функцию длины, мы сводим список к одному значению. Это цель fold.
(define (length l)
(foldr (lambda (_ cur-length) ( 1 cur-length)) 0 l))
Когда вы думаете о foldr, вам следует подумать об этом, просто заменив cons в списке функцией, а пустой список аргументом базового варианта. Возьмем следующий пример:
'(1 2 3 4)
= (cons 1 (cons 2 (cons 3 (cons 4 '()))))
(foldr f base '(1 2 3 4))
= (f 1 (f 2 (f 3 (f 4 base))))
Оказывается, foldl также работает в этом случае, потому что мы просто добавляем по одному для каждого элемента, не имеет значения, идем ли мы слева направо или справа налево.
(define (length l)
(foldl (lambda (_ cur-length) ( 1 cur-length)) 0 l))