SML: Сравнение каждого элемента двух списков без сохранения информации о состоянии? - PullRequest
0 голосов
/ 04 марта 2019

У меня есть назначение SML, и общая идея заключается в том, что я не должен хранить информацию о состоянии, не должен использовать встроенные функции библиотеки и т. Д., А просто решать функционально.Не уверен, как это сделать:

Вопрос требует сравнения каждого элемента двух списков вместе:

input

list1: [(3,3,5), (5, 4,7), (2,3,4)];list2: [3, 6];

output

newList: [(3,3,5), (2,3,5)]

По существу, когдаВторой элемент в кортеже list1 соответствует элементу в списке 2, затем я должен добавить элемент list1 в новый список вывода.

Способ реализации:

fun thing(x, y) = 
   if null x then []
   else if #2 (hd x) = (hd y) then hd x @ thing(tl x, y)
   else thing(tl x, y);

Очевидно, что проблема заключается в том, что я теряю информацию о состоянии: как бы вы сопоставили каждый элемент в list1 с каждым элементом в list2?

1 Ответ

0 голосов
/ 04 марта 2019

когда второй элемент в аргументе кортежа list1 соответствует элементу в списке 2,
, тогда я должен добавить элемент list1 в новый список вывода.

fun thing(x, y) = 
  if null x then []
  else if #2 (hd x) = (hd y) then hd x @ thing(tl x, y)
  else thing(tl x, y);

Вместоif null x then ..., hd x и tl x, используйте сопоставление с шаблоном:

fun thing ([], _) = ...
  | thing ((x,y,z)::haystack, needles) = ...

Чтобы выяснить, является ли y членом needles, создайте функцию принадлежности:

fun elem (p, []) = false
  | elem (p, q::qs) = p = q orelse elem (p, qs)

Проверьте, если elem (y, needles), чтобы определить, следует ли включать (x,y,z) как часть вашего результата.

Применить thing рекурсивно к haystack и needles.

Составьте рекурсивный результат, используя оператор :: (cons) вместо @ (append).


Вот как можно решить это упражнение с библиотечными функциями:

fun curry f x y = f (x, y)
fun thing (haystack, needles) =
    List.filter (fn (x,y,z) =>
      List.exists (curry op= y) needles) haystack
...