Широкие карты и манипуляции с фильтрами в списках - ML

Я пытался создать функцию ML (карри), которая берет список кортежей из формы: (предикат, функция) и список и возвращает операцию функции каждого элемента, который вернул true, то есть для каждого условия есть определенный функцию для выполнения, например:

    - map_many [(fn x => x mod 2 = 0, fn x => x*2), (fn x => x mod 3 = 0, fn x => x+5), (fn x => x mod 4 = 0, fn x => x*x)] [1,2,3,4,5,6,7,8,9,10];

val it = [1,4,8,64,5,17,7,256,14,20] : int list

Это то, что я пытался сделать, но это не сработало:

fun map_many _ [] = []
  | map_many [] _ = []
  | map_many ((y,z)::ys) (x::xs) =

    if (y(x) = true)
        then z(x)::map_many ys xs
    else
        x::map_many ys xs; 

Что я делаю неправильно?

1 ответ

Решение

Это даст желаемый результат.

fun map_one [] (old,x) = x
  | map_one ((p,f)::fs) (old,x) = 
      if p old
      then map_one fs (old,(f x))
      else map_one fs (old,x)

fun map_many _ [] = []
  | map_many fs (x::xs) = map_one fs (x,x) :: map_many fs xs

Обратите внимание, что map_one использует кортеж int*int отслеживать старое значение (которое вы используете в своих предикатах) и сгенерированное значение.


Ваш код использовал каждую пару функций только один раз, а каждый номер - один раз. Вы всегда ставили ys а также xs в рекурсивную функцию, запуская их с той же скоростью, а не опуская первую, опуская один раз на вторую, а затем снова опуская первую. Вы выполняли max(length(ys),length(xs)) операции, когда вы хотели сделать length(ys)*length(xs),

Другие вопросы по тегам