
Vladimir
14.09.2018
06:27:08

Evgeniy
14.09.2018
06:30:32
Привет.

Валентин
14.09.2018
06:30:53
Приветствую!
Я надеюсь, что меня тут тряпками не закидают за глупый вопрос. Только начинаю изучать язык.
Почему это код возвращает функцию, а не результат функции?
let m = 12345
let digits n = tostr m >> Seq.toList >> List.map (fun u -> int u - int '0') >> List.item n
let result = digits 2
printfn "%A" result

Google

Fill
14.09.2018
06:51:06
Из-за оператора композиции ">>"
Замени на "|>"

Валентин
14.09.2018
06:53:27
В таком случае на Seq.toList ругается: The type 'unit -> string' is not compatible with the type 'seq<'a>'

Fill
14.09.2018
06:54:30
tostr возвращает string?

Валентин
14.09.2018
06:57:55
Совершенно верно, проблема была в tostrе) Но я всё равно не могу понять как из композиции функций вернуть результат?

Fill
14.09.2018
06:58:39
Композиция возвращает новую функцию
По ее сигнатуре можно понять, какие параметры она принимает
И скормить их ей
Вот тебе и результат

Валентин
14.09.2018
06:59:37
int -> 'c -> int

Ayrat
14.09.2018
07:24:38

Валентин
14.09.2018
07:33:52
Только let tostr n = m.ToString(), или даже let tostr _ = m.ToString()
Но параметр m он получает из замыкания (как я подозреваю), но тем не менее digits всё равно требует второй параметр, причём не важно что туда передать, т.к. он игнорируется

Vasily
14.09.2018
07:34:16
Тут нет замыканий

Google

Vasily
14.09.2018
07:36:09
Ты лучше скажи, что хочешь получить на выходе

Валентин
14.09.2018
07:39:21

Vasily
14.09.2018
07:50:57
Смотри, цепочка следующая : На входе у функции два параметра
Число и количество разрядов
Про то, в каком им порядке лучше идти, пока не будем обсуждать
Дальше
Число надо преобразовать в строку
Взять у нее второй символ
Точнее n-ный
И преобразовать в число
Обратно
число в строку преобразуется тривиально
string n
Такс, напишу-ка я gist

Artemy
14.09.2018
07:55:53
Да, аналог tostr уже в стандартной библиотеке есть — функция string

Vasily
14.09.2018
07:57:32
let digit n number=
number
|>string
|>Seq.item n
|> (fun c->int c-int '0')
Вот это минимально работает
Дальше уже куча нюансов
Типа проверки на длину этц

Friedrich
14.09.2018
08:40:17

Google

Валентин
14.09.2018
08:40:27
Спасибо! Я пытался провернуть это через композицию функций, пока не получилось

Vasily
14.09.2018
08:40:39

Artemy
14.09.2018
08:42:01

Валентин
14.09.2018
08:43:20

Vasily
14.09.2018
08:43:55
@fvnever Затих шота

Friedrich
14.09.2018
08:44:12
Я просто задыхался от гнева :)

Vasily
14.09.2018
08:44:24
А, ты про аллокации

Friedrich
14.09.2018
08:44:32
Ну, это же можно математикой решить

Vasily
14.09.2018
08:44:38
Ну на пайпах можно

Artemy
14.09.2018
08:44:41

Vasily
14.09.2018
08:44:47
А можно и математикой

Friedrich
14.09.2018
08:44:53
Решается десятичным логарифмом и остатком от деления.

Vasily
14.09.2018
08:45:06
Угу

Friedrich
14.09.2018
08:45:18
Конечно, логарифм ещё хочется помикрооптимизировать, но это уже будет на порядки лучше, чем выделение стрингов в куче :)

Vasily
14.09.2018
08:45:22
Тоскуешь, видать, по моргу-то

Friedrich
14.09.2018
08:46:03

Валентин
14.09.2018
08:46:19

Vasily
14.09.2018
08:46:47
В целом, я согласен с @fvnever , что задача решается неоптимальным образом
С т.з. выделения памяти

Google

Vasily
14.09.2018
08:47:14
Кстати

Roman
14.09.2018
08:47:18
ну, это если без логарифмов

Vasily
14.09.2018
08:47:41

Roman
14.09.2018
08:47:43
хотя там еще надо на - проверить первый символ

Vasily
14.09.2018
08:47:50
Дальше, естественно, опшны и прочее

Vlad
14.09.2018
08:48:25
именно

Ayrat
14.09.2018
08:49:17

Vasily
14.09.2018
08:49:23
Во-во

Artemy
14.09.2018
08:49:27
Валентин вот, например, здесь:
let digit n number=
number
|>string
|>Seq.item n
|> (fun c->int c-int '0')
чётко видно, что `number` можно с обеих сторон сократить. И в результате получить:
let digit n =
string
>> Seq.item n
>> fun c -> int c - int '0'

Friedrich
14.09.2018
08:49:30

Vasily
14.09.2018
08:49:31
Согласен с предыдущим оратором

Artemy
14.09.2018
08:50:37
Блин, я с форматированием запутался

Vasily
14.09.2018
08:51:12
К тому же, в твоей функции не будет явно задан тип аргумента
Скорее всего
А выведет по первому переданному

Artemy
14.09.2018
08:52:05
Да, тип уже обобщённый: 'a -> 'b -> 'c
Но Валентин же хотел именно композицией, потому и привёл соответствующий пример

Google

Vasily
14.09.2018
08:53:36
Я вот как-то композицию не очень люблю

Валентин
14.09.2018
08:53:49

Vasily
14.09.2018
08:54:09
Композиция - это склейка нескольких функций в одну
Пайпинг - передача результата одной функции на вход другой

Artemy
14.09.2018
08:54:30
Мне нравится в некоторых случаях. Например, для отрицания. (not << isDigit) x читается приятнее, чем x |> isDigit |> not

Vasily
14.09.2018
08:54:42
Тут согласен

Artemy
14.09.2018
08:55:32
Ну а во многих случаях, да, композиция может запутать
Всё-таки параметры опускаются и ты в коде их не видишь

Валентин
14.09.2018
08:57:16

Artemy
14.09.2018
08:58:08
У композиции оба аргумента — функции. У пайпа же один параметр — значение, а другой — функция

Валентин
14.09.2018
09:00:53
Чем sin(sqr(2)) отличается от sin(4)?

Artemy
14.09.2018
09:01:51
Структурой выражения
Но по результату не отличаются

Александр
14.09.2018
09:02:39

Валентин
14.09.2018
09:03:31

Vasily
14.09.2018
09:06:33
Прими то, что переменных нет
Есть функции
И сразу станет проще
let num=5
Тоже функция