Поиск:

Ответ в темуСоздание новой темы Создание опроса
> [F#] Простые вопросы 
:(
    Опции темы
laMer007
Дата 27.12.2011, 20:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 3
Регистрация: 27.12.2011

Репутация: нет
Всего: нет



Мне нравится F#. Но большой практики написания программ на нём не было. Писал только вспомогательные тулзы для проектов.

В этой теме хочу задавать вопросы по этому языку.


И так, первые вопросы:
1)Есть ли в F# функция высшего порядка, подобная std::find_if?
2)Как из тела цикла возвращать значение, если искомый результат обнаруживается в конце или в середине цикла? 
Пример, когда результат обнаруживается в конце цикла:
Код
let num n = 
  let t = [|for i in 1..n -> i*2|]
  t.[t.Length-1]
System.Console.Write(num 5)

(Понятно, что тут должен быть поиск в каком-нибудь массиве, но это просто пример).
3)Как правильно получить последний элемент массива, не используя такую убогую конструкцию t.[t.Length-1]?
4)Как вы возвращаете значение из сложной функции с несколькими циклами и ветвлениями, ведь return нет в языке? Мне приходилось делать хак в виде присвоения мутабильной переменной result результата с последующим киданием исключения и отловом около последней строки функции, возвращающей этот сохраненный ранее result. Простите, мой испорченный императивными языками стиль программирования. Как сделать возврат значения из относительно сложной функции правильно по функциональному?

Это сообщение отредактировал(а) laMer007 - 28.12.2011, 01:12
PM MAIL   Вверх
k0rvin
Дата 27.12.2011, 21:40 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 442
Регистрация: 24.1.2010

Репутация: нет
Всего: 5



Цитата(laMer007 @ 27.12.2011,  20:16)
1)Есть ли в F# функция высшего порядка, подобная std::find_if?

наверное этот ответ(как и другие) легко найти в описании языка, впрочем можно и самому написать, заодно и попрактиковался бы
Код

let rec find_if predicate xs =
    match xs with
    | [] -> None
    | hd::tl ->
        match predicate hd with
        | true  -> Some(hd)
        | false -> find_if predicate tl

как же ты писал тулзы для проектов?


--------------------
“Object-oriented design is the roman numerals of computing.” — Rob Pike
All software sucks
PM MAIL   Вверх
laMer007
Дата 28.12.2011, 01:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 3
Регистрация: 27.12.2011

Репутация: нет
Всего: нет



Цитата('k0rvin')
этот ответ легко найти в описании языка 
Не, не легко. Я думаю, в F# обобщённых функций в стандартной библиотеке нет. Про Array.find я знаю. Вы для List свой велосипед написали, но для него такая функция тоже есть. Но это все не то.

Ладно. А что с другими вопросами 2-4? Если они не очень понятны, то я могу объяснить подробнее с конкретными примерами.

Это сообщение отредактировал(а) laMer007 - 28.12.2011, 01:11
PM MAIL   Вверх
k0rvin
Дата 28.12.2011, 08:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 442
Регистрация: 24.1.2010

Репутация: нет
Всего: 5



Цитата(laMer007 @ 28.12.2011,  01:07)
Не, не легко. Я думаю, в F# обобщённых функций в стандартной библиотеке нет. Про Array.find я знаю. Вы для List свой велосипед написали, но для него такая функция тоже есть. Но это все не то.

что значит "не то"? и что ты подразумеваешь под обобщенными функциями?


--------------------
“Object-oriented design is the roman numerals of computing.” — Rob Pike
All software sucks
PM MAIL   Вверх
k0rvin
Дата 28.12.2011, 09:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 442
Регистрация: 24.1.2010

Репутация: нет
Всего: 5



3) опять же, ищите или пишите функцию last

Добавлено @ 09:23
2,4) думаю смотреть нужно в сторону продолжений (continuations), как-то так

Это сообщение отредактировал(а) k0rvin - 28.12.2011, 12:59


--------------------
“Object-oriented design is the roman numerals of computing.” — Rob Pike
All software sucks
PM MAIL   Вверх
laMer007
Дата 28.12.2011, 14:12 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 3
Регистрация: 27.12.2011

Репутация: нет
Всего: нет



Цитата(k0rvin @  28.12.2011,  08:43 Найти цитируемый пост)
что значит "не то"? и что ты подразумеваешь под обобщенными функциями? 
Пример:
Код
auto pred=[](int v){return v%4==0;};

int main(void)
{
  int ca[]={1,2,3,7,4,6};
  array<int,6> a={{1,8,3,4,4,6}};
  vector<int> v={1,2,2,4,44,6};
  list<int> l={1,2,8,4,7,6};
  deque<int> d={1,3,3,8,5,6};
  cout<<*find_if(begin(ca), end(ca), pred)<<endl;
  cout<<*find_if(begin(a), end(a), pred)<<endl;
  cout<<*find_if(begin(v), end(v), pred)<<endl;
  cout<<*find_if(begin(l), end(l), pred)<<endl;
  cout<<*find_if(begin(d), end(d), pred)<<endl;
Как видите функция std::find_if работает для любого типа контейнера и всегда тип контейнера можно поменять без необходимости каких либо изменений в коде. В F# же приходится, например по всему коду заменять Array.find на List.find, если поменял тип контейнера с массива на список.


Цитата(k0rvin @  28.12.2011,  09:11 Найти цитируемый пост)
опять же, ищите или пишите функцию last
Не нашёл такой функции что-то для массивов. Понятно, что всё можно написать самому, но наиболее приятно пользоваться языком, если такие мелочи, как last есть в стандартной библиотеке.


Цитата(k0rvin @  28.12.2011,  09:11 Найти цитируемый пост)
2) думаю смотреть нужно в сторону продолжений (continuations) 
Спасибо:
Код
let findModM arr n = seq{ for i in arr do if i%n=0 then yield i}
System.Console.Write(findModM [1..50] 5 |> Seq.head)
Лучше не написать?


Цитата(k0rvin @  28.12.2011,  09:11 Найти цитируемый пост)
4) думаю смотреть нужно в сторону продолжений (continuations) 
А можете накатать примерчик решения 4го вопроса, пожалуйста?


Это сообщение отредактировал(а) laMer007 - 28.12.2011, 14:19
PM MAIL   Вверх
k0rvin
Дата 28.12.2011, 14:42 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 442
Регистрация: 24.1.2010

Репутация: нет
Всего: 5



Цитата(laMer007 @ 28.12.2011,  14:12)
Пример:
Код
auto pred=[](int v){return v%4==0;};

int main(void)
{
  int ca[]={1,2,3,7,4,6};
  array<int,6> a={{1,8,3,4,4,6}};
  vector<int> v={1,2,2,4,44,6};
  list<int> l={1,2,8,4,7,6};
  deque<int> d={1,3,3,8,5,6};
  cout<<*find_if(begin(ca), end(ca), pred)<<endl;
  cout<<*find_if(begin(a), end(a), pred)<<endl;
  cout<<*find_if(begin(v), end(v), pred)<<endl;
  cout<<*find_if(begin(l), end(l), pred)<<endl;
  cout<<*find_if(begin(d), end(d), pred)<<endl;
Как видите функция std::find_if работает для любого типа контейнера и всегда тип контейнера можно поменять без необходимости каких либо изменений в коде. В F# же приходится, например по всему коду заменять Array.find на List.find, если поменял тип контейнера с массива на список.

а, ты про это... это не "обобщенная функция", ну да не суть. я не знаю как там в F#, но наверное типы Array и List наследуются от одного какого-то общего предка Container или Collection, в котором определена find. иначе придется писать свои обертки.

мб просто преобразовывать в Sequence и юзать Seq.find

Добавлено @ 14:45
Цитата(laMer007 @ 28.12.2011,  14:12)
Не нашёл такой функции что-то для массивов. Понятно, что всё можно написать самому, но наиболее приятно пользоваться языком, если такие мелочи, как last есть в стандартной библиотеке.

а зачем раздувать стандартную библиотеку кучей мелочей? может быть у майкрософт есть набор дополнительных библиотек, где собраны различные полезные утилиты, не вошедшие в стандартную?

Цитата(laMer007 @ 28.12.2011,  14:12)
Лучше не написать?
А можете накатать примерчик решения 4го вопроса, пожалуйста?

хз, я не шарю в F#

Это сообщение отредактировал(а) k0rvin - 28.12.2011, 14:46


--------------------
“Object-oriented design is the roman numerals of computing.” — Rob Pike
All software sucks
PM MAIL   Вверх
Kakadu
Дата 28.12.2011, 15:29 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 273
Регистрация: 19.3.2008

Репутация: нет
Всего: 7



Цитата

1)Есть ли в F# функция высшего порядка, подобная std::find_if?

Нет, для каждого контейнера (array, list, seq, etc) надо реализовывать свой поиск. естественно, желательно с той же сигнатурой. Тогда типовыводилка тип выведет и будет визуально как в плюсах.
Цитата

2)Как из тела цикла возвращать значение, если искомый результат обнаруживается в конце или в середине цикла? 
Пример, когда результат обнаруживается в конце цикла:
Код
let num n = 
  let t = [|for i in 1..n -> i*2|]
  t.[t.Length-1]
System.Console.Write(num 5)

(Понятно, что тут должен быть поиск в каком-нибудь массиве, но это просто пример).

Про yeild_return для Ocaml в блоге JaneStreet Capitals
Цитата

3)Как правильно получить последний элемент массива, не используя такую убогую конструкцию t.[t.Length-1]?

Думаю так и получать. Но мне ни разу это пока не пригождалось. можно ещё List.reverse + List.head
Цитата
4)Как вы возвращаете значение из сложной функции с несколькими циклами и ветвлениями, ведь return нет в языке? Мне приходилось делать хак в виде присвоения мутабильной переменной result результата с последующим киданием исключения и отловом около последней строки функции, возвращающей этот сохраненный ранее result. Простите, мой испорченный императивными языками стиль программирования. Как сделать возврат значения из относительно сложной функции правильно по функциональному?

кидание исключений в Ocaml это норм, в диезе думаю тоже. Мутабельное значение иногда некрасиво. Ну и про yeild_return можно подумать.


--------------------
Добрые мариносы долго кормили украдкой маленьких зерлингов. От этой украдки зерлинги пухли и дохли
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума «Функциональные языки: общие вопросы»
Void
  • Пожалуйста, создавайте темы с содержательными названиями. Если у Вас вопрос по конкретному языку, укажите его в заголовке, например: «[Haskell] Как использовать монаду State».
  • Уважаемые учащиеся, здесь всегда рады помочь Вам, но не делать за Вас вашу работу. У вас гораздо больше шансов получить помощь, если Вы приложите усилия и поделитесь с нами проблемами и результатами. В противном случае добро пожаловать в раздел Центр Помощи.
  • Получив ответ на интересующий Вас вопрос, не забудьте пометить его как решённый.

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Void.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Функциональные языки: общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.1375 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.