2017-02-15 56 views
2

Я пытаюсь сравнить строку с Charlist в SML, используя REPL у меня есть это:SML Содержит используя строку и Charlist

val alphabet = "abcdefghijklmnopqrstuvwxyz"; 
val charalphabet = explode alphabet; 
val str = "the quick brown fox"; 
val res = Char.contains(str, charalphabet); 

Это выдает ошибку, потому что я пытаюсь сравнить строку с Charlist, и содержит только сравнение String с одним Char. Кто-нибудь есть идеи, как обойти это? Я мог бы взорвать String str и сравнить списки Char, но я не уверен, что их функция для этого. Поэтому, если у кого-нибудь есть идеи о функциях или вещах, которые я могу прочитать, пожалуйста, дайте мне знать, цель состоит в том, чтобы увидеть, содержит ли String определенный Charlist.

Я чрезвычайно новичок в SML, поэтому любая помощь очень ценится!

+0

Есть ли причина, по которой 'wxyz' отсутствует в вашем алфавите? В любом случае: подсказка 1: «List.all» полезен. Подсказка 2: 'Char.contains str' - это функция типа' char -> bool'. –

+0

Я отредактировал сообщение, пропавший "wxyz" был опечатан мной. Я рассмотрю две вещи, которые вы только что упомянули. Функция, которой я раньше была сегодня, была: fun isPangram c = if Char.содержит (c, charalphabet), тогда true else false; находится на правильном пути, хотя он не работает? – firetiger443

+0

Да, это на правильном пути в том смысле, что 'Char.contains' является естественным инструментом для работы, и вы знаете, что проблема с вашим текущим кодом. Но учтите, что 'Char.contains' является карриной функцией, поэтому помещать скобки вокруг входных данных, подобных этому, неверно, поэтому у вас есть еще одна проблема в дополнение к проблеме с символом char или with. –

ответ

1

Способ, которым вы помещаете круглые скобки и помещаете запятую между аргументами Char.contains, предполагает, что у вас возникли проблемы с пониманием того, как работают функции Char.contains. Такие функции называются карри-функциями, и это несколько вводит в заблуждение, если вы думаете о них как функции двух переменных.

Char.contains является функцией типа string -> char -> bool. Тип ввода - это строка, а ее тип вывода - это функция типа char -> bool. Чаще всего эта функция выхода мгновенно оценивается:

- Char.contains "cat" #"a"; 
val it = true : bool 

Что может выглядеть, как вы оцениваете функцию 2-х переменных, но в действительности вы оцениваете 2 функции 1 переменной: функции Char.contains является evalauted на "cat" для возврата функции типа char -> bool, и эта последняя функция оценивается как #"a", чтобы получить окончательный результат.

Обратите внимание, что можно использовать Char.contains для возврата функции, которую не является сразу же оценивается. Например:

val isVowel = Char.contains "aeiou"; 

isVowel Вот это функция, которая может быть использована для проверки, если (в нижнем регистре) символ является гласной.

List.all является функцией типа ('a -> bool) -> 'a list -> bool. Чтобы использовать его, чтобы проверить, удовлетворяют ли все элементы, если список заданного типа (например, char) удовлетворяют свойству, вам необходимо передать ему функцию, которая принимает элементы этого типа и возвращает логическое значение (например, функцию типа char -> bool;

Но - мы уже знаем, как производить функции типа char -> bool: использовать Char.contains для любой строки s, Char.contains s это функция, которая может быть передана List.all и затем полученную функцию, применяемую к списку символов в алфавите:.

val alphabet = explode "abcdefghijklmnopqrstuvwxyz"; 
fun isPanagram s = List.all (Char.contains s) alphabet; 

Причина, по которой Char.contains s заключен в круглые скобки, так как оценка функции лево-ассоциативная. Без круглых скобок SML будет анализировать его как (List.all Char.contains) s, что не имеет смысла.

+0

Большое спасибо за подробный ответ/объяснение. С некоторыми изменениями, которые вы рекомендовали, я получил свою функцию отлично. Еще раз спасибо за то, что вы наклеились на меня и нашли время, чтобы все объяснить так хорошо! – firetiger443