F# - A Functional Programming Language
От: G2 Ниоткуда  
Дата: 18.10.07 07:03
Оценка:
This is one of the best things that has happened at Microsoft ever since we created Microsoft Research over 15 years ago. Here is another great example of technology transfer at work. We will be partnering with Don Syme and others in Microsoft Research to fully integrate the F# language into Visual Studio and continue innovating and evolving F#. In my mind, F# is another first-class programming language on the CLR.
Улыбаемся и машем :-)
Re: F# - A Functional Programming Language
От: Кодёнок  
Дата: 18.10.07 08:13
Оценка:
Кто-нить объяснит, зачем ml требует писать «let rec». Неужели и так не ясно, rec или не rec.
Re: F# - A Functional Programming Language
От: VladD2 Российская Империя www.nemerle.org
Дата: 18.10.07 09:13
Оценка: -2
Здравствуйте, G2, Вы писали:

G2>This is one of the best things that has happened at Microsoft ever since we created Microsoft Research over 15 years ago. Here is another great example of technology transfer at work. We will be partnering with Don Syme and others in Microsoft Research to fully integrate the F# language into Visual Studio and continue innovating and evolving F#. In my mind, F# is another first-class programming language on the CLR.


Проснулся милок?

Это новости уже лет пять.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[2]: F# - A Functional Programming Language
От: Schade Россия  
Дата: 18.10.07 09:41
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Это новости уже лет пять.


Эта как раз-таки свежая. Раньше развитием языка занимался фактически один человек, теперь MS решила повернуться к нему если не лицом, то уж хотя бы не задом, и предоставить больше ресурсов для развития (хотя, конечно, в мэйнстрим ему не попасть).

Кстати, F# здорово изменился за последнее время.
Re[2]: F# - A Functional Programming Language
От: G2 Ниоткуда  
Дата: 18.10.07 09:41
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Это новости уже лет пять.


Что — то тогда долго они его интегрировали в VS.
Улыбаемся и машем :-)
Re[2]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 11:47
Оценка:
Здравствуйте, Кодёнок, Вы писали:


Кё>Кто-нить объяснит, зачем ml требует писать «let rec». Неужели и так не ясно, rec или не rec.

В ML следующий код создает 3 разные переменные foo:
let foo = 1
let _ = print_int foo (* печатает 1 *)

let foo = foo + 1
let _ = print_int foo (* печатает 2 *)

let foo = foo + 2
let _ = print_int foo (* печатает 4 *)
Re[3]: F# - A Functional Programming Language
От: Кодёнок  
Дата: 18.10.07 12:33
Оценка:
Здравствуйте, palm mute, Вы писали:

Кё>>Кто-нить объяснит, зачем ml требует писать «let rec». Неужели и так не ясно, rec или не rec.


я про рекурсивные функции
Re[4]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 13:17
Оценка: 12 (2)
Здравствуйте, Кодёнок, Вы писали:

Кё>Здравствуйте, palm mute, Вы писали:


Кё>>>Кто-нить объяснит, зачем ml требует писать «let rec». Неужели и так не ясно, rec или не rec.


Кё>я про рекурсивные функции

А что меняется? Функции — не функции — это неважно, все дело в видимости имен. Хорошо, изменим пример.

Теперь у нас будут 3 разных функции foo:
let foo () = 1
let _ = print_int (foo ())

let foo () = foo () + 1
let _ = print_int (foo ())

let foo () = foo () + 2
let _ = print_int (foo ())

Вывод этого кода такой же, как и в предыдущем случае.
Функция let foo () = foo () + 1 вызывает одноименную функцию foo, определенную выше. Функция let rec foo () = foo () + 1 вызывает сама себя.
Re[2]: F# - A Functional Programming Language
От: EvilChild Ниоткуда  
Дата: 18.10.07 14:01
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Проснулся милок?

Ты как обычно по ссылкам не ходишь, милок? Вся соль в этом:

Somasegar, the head of the Developer Division at Microsoft, has announced the productization of F#.

Re[5]: F# - A Functional Programming Language
От: no4  
Дата: 18.10.07 14:41
Оценка:
Здравствуйте, palm mute, Вы писали:

Кё>>я про рекурсивные функции

PM>А что меняется? Функции — не функции — это неважно, все дело в видимости имен. Хорошо, изменим пример.

А в форте для этого было спецслово RECURSE — оно не декларировалось рекурсивным, а просто для того, чтобы позвать себя надо было писать RECURSE. Кстати, интересно, что в ML надо сделать, чтоб звать как себя так и предыдущий вариант одноименной функции?
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re[6]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 14:49
Оценка:
Здравствуйте, no4, Вы писали:

no4>Кстати, интересно, что в ML надо сделать, чтоб звать как себя так и предыдущий вариант одноименной функции?

перед определением рекурсивной функции старую переименовать:
let foo _ = ...
let foo_old = foo
let rec foo = ... (foo_old x) ... (foo y)


Хотя обычно такой проблемы не возникает, обычно все функции имеют различные имена. Потому Хаскелевский подход — все определения верхнего уровня обернуть в неявный letrec — вызывает меньше вопросов.
Re[2]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 15:14
Оценка: 7 (1)
Здравствуйте, Кодёнок, Вы писали:

Кё>Кто-нить объяснит, зачем ml требует писать «let rec». Неужели и так не ясно, rec или не rec.

Вот игрушечный интерпретатор ML-подобного языка. Обратите внимание, насколько по-разному обрабатываются конструкции let и letrec в энергичном языке.
В ленивом языке гораздо проще выбросить let и оставить только letrec, т.к. бОльшие классы рекурсивных значений имеют смысл. Если же компилятор будет автоматически выбирать между let и letrec, это усложнит и сделает непоследовательными правила поиска имен для обычных и функциональных значений.
type varname = string
type expr =
    Int of int                      |
    Bool of bool                    |
    Var of varname                  |
    Plus of expr * expr             |
    Mult of expr * expr             |
    Eq of expr * expr               |
    If of expr * expr * expr        |
    Lambda of varname * expr        |
    Application of expr * expr      |
    Let of varname *expr * expr     |
    LetRec of varname * expr * expr

type value = VInt of int | VBool of bool | VClosure of (value -> value)
type binding = varname * value
type environment = binding list

exception EvalError of string

let error msg = raise (EvalError msg)
let internal_error () = failwith "The world is upside down"

let lookup_var (var : varname) (env : environment) : value =
  try
    List.assoc var env
  with Not_found -> error ("Unbound variable " ^ var)


let rec eval (e : expr) (env : environment) : value = match e with
  | Int x    -> VInt x
  | Bool x   -> VBool x
  | Var name -> lookup_var name env
  | Plus (e1, e2) ->
        (match (eval e1 env, eval e2 env) with
           | (VInt x, VInt y) -> VInt (x+y)
           | _                -> error "Non-int in addition")
  | Mult (e1, e2) ->
        (match (eval e1 env, eval e2 env) with
           | (VInt x, VInt y) -> VInt (x*y)
           | _                -> error "Non-int in multiplication")
  | Eq (e1, e2) ->
        (match (eval e1 env, eval e2 env) with
           | (VInt x, VInt y) -> VBool (x==y)
           | _                -> error "Non-int in comparision")
  | If (cond, thenExpr, elseExpr) ->
        (match eval cond env with
           | VBool x   -> if x then eval thenExpr env
                               else eval elseExpr env
           | _         -> error "Non-boolean in conditional")
  | Lambda (var, body) ->
        VClosure (fun x -> eval body ((var, x)::env))
  | Application (func, arg) ->
        (match eval func env with
          | VClosure f -> f (eval arg env)
          | _          -> error "Non-function in application")
  | Let (var, value, body) ->
        eval body ((var, eval value env)::env)
  | LetRec (var, value, body) ->
        (match value with
           | Lambda _ ->
                 let rec new_env =
                   let rec func x = 
                     match eval value new_env with
                       | VClosure f -> f x
                       | _ -> internal_error ()
                   in ((var, VClosure func)::env)
                 in eval body new_env
           | _ -> error "Only functions are allowed on the right-hand side of letrec")

(*** tests *********************************)

(* fun n -> if n==0 then 1 else n * fact (n + (-1)) *)
let (factorial_body : expr) =
  (Lambda ("n",
           If (Eq (Var "n", Int 0),
               Int 1,
               (Mult (Var "n",
                      Application (Var "fact",
                                   Plus (Var "n", Int (-1))))))))


let tests =
  [
      (* let x = 5 in x + 4 *)
      Let ("x", Int 5, Plus (Var "x", Int 4));

      (* non-recursive function: let f = fun x -> x*2 in f 4 *)
      Let ("f", Lambda ("x", Mult (Var "x", Int 2)), Application (Var "f", Int 4));

      (* incorrect factorial *)
      Let ("fact", factorial_body, (Application (Var "fact", Int 5)));

      (* correct factorial *)
      LetRec ("fact", factorial_body, (Application (Var "fact", Int 5)));
  ]

let print_val = function
  | VInt n     -> print_int n
  | VBool b    -> print_string (if b then "true" else "false")
  | VClosure _ -> print_string "<function>"


let run_eval expr =
  try
    (print_val (eval expr []);
     print_endline "")
  with EvalError msg -> print_endline msg


let main () =  List.iter run_eval tests

let _ = main ()
Re[3]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 15:32
Оценка: :)
Здравствуйте, palm mute, Вы при обсуждении вопроса "зачем нужен rec" вставили в код лишний rec — иронично, не правда ли?:


PM>  | LetRec (var, value, body) ->
PM>        (match value with
PM>           | Lambda _ ->
PM>                 let rec new_env =
PM>                   let (* rec *) func x = (* здесь rec ни к чему *)
PM>                     match eval value new_env with
PM>                       | VClosure f -> f x
PM>                       | _ -> internal_error ()
PM>                   in ((var, VClosure func)::env)
PM>                 in eval body new_env
PM>           | _ -> error "Only functions are allowed on the right-hand side of letrec")
Re[3]: F# - A Functional Programming Language
От: konsoletyper Россия https://github.com/konsoletyper
Дата: 18.10.07 16:55
Оценка:
Здравствуйте, palm mute, Вы писали:

PM>Вот игрушечный интерпретатор ML-подобного языка. Обратите внимание, насколько по-разному обрабатываются конструкции let и letrec в энергичном языке.

PM>В ленивом языке гораздо проще выбросить let и оставить только letrec, т.к. бОльшие классы рекурсивных значений имеют смысл. Если же компилятор будет автоматически выбирать между let и letrec, это усложнит и сделает непоследовательными правила поиска имен для обычных и функциональных значений.

Вот неужели трудно было сделать примитивнейшую оптимизацию, посчитав любой let за let rec, а потом автоматически выбросив rec у нерекурсивных (или у не взаимно рекурсивных) функций?
... << RSDN@Home 1.2.0 alpha rev. 710>>
Re[4]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 17:50
Оценка:
Здравствуйте, konsoletyper, Вы писали:

K>Вот неужели трудно было сделать примитивнейшую оптимизацию, посчитав любой let за let rec, а потом автоматически выбросив rec у нерекурсивных (или у не взаимно рекурсивных) функций?


let rec не имеет смысла для значений других типов (ОКамл позволяет создавать циклические структуры данных, но с жесткими ограничениями, справа от знака "=" не может быть вызовов функций, только конструкторы и значения, в SML, насколько я знаю, рекурсивными могут быть только функции).

Поэтому, если делать все функции автоматически рекурсивными, мы получаем разные правила поиска имен для функций и для "простых" значений:
let x = 1
let x = x + 5 (* здесь x справа от '=' ссылается на переменную x 
                 в области видимости, результат = 6 *)

let foo x = x 
let foo x = if x > 0 then x * foo (x-1) (* а здесь, по-твоему, должен быть рекурсивный вызов - 
                                           с какой стати? функции - это те же переменные,
                                           поиск имен должен работать однообразно независимо от типа *)
Re[5]: F# - A Functional Programming Language
От: palm mute  
Дата: 18.10.07 18:16
Оценка: 2 (1)
Здравствуйте, palm mute, Вы писали:

K>>Вот неужели трудно было сделать примитивнейшую оптимизацию, посчитав любой let за let rec, а потом автоматически выбросив rec у нерекурсивных (или у не взаимно рекурсивных) функций?


PM>let rec не имеет смысла для значений других типов (ОКамл позволяет создавать циклические структуры данных, но с жесткими ограничениями, справа от знака "=" не может быть вызовов функций, только конструкторы и значения, в SML, насколько я знаю, рекурсивными могут быть только функции).


Кроме того, не все функции являются синтаксическими функциями.
(* понять, что sum - это функция, можно только после вывода типов,
   который, естественно, делается уже при построенном AST. 
   различие между let и letrec - синтаксическое.
 *)
let sum = List.fold_left (+) 0 

(* а теперь представим себе следующую ситуацию *)
let foo f y z = ...

let bar = ...

let bar = foo bar (* какой bar здесь имеется в виду? bar - функция, но на основании 
                     одного лишь синтаксиса это определить невозможно *)


Таких проблем нет в C#, Java (или даже Nemerle), но там и конструкции let .. in нет.
В Хаскеле let .. in есть (а также есть where), но Haskell — ленивый.
Re[2]: F# - A Functional Programming Language
От: geniepro http://geniepro.livejournal.com/
Дата: 18.10.07 19:01
Оценка:
Здравствуйте, Кодёнок, Вы писали:

Кё>Кто-нить объяснит, зачем ml требует писать «let rec». Неужели и так не ясно, rec или не rec.


Видимо, это традиция, пошедшая ещё с лиспов, где тоже есть let и letrec ...
Re[3]: F# - A Functional Programming Language
От: VladD2 Российская Империя www.nemerle.org
Дата: 19.10.07 20:33
Оценка:
Здравствуйте, EvilChild, Вы писали:

EC>Ты как обычно по ссылкам не ходишь, милок? Вся соль в этом:


Может быть. Просто интеграция у него была очень давно. Фиговая, првда.

EC>

EC>Somasegar, the head of the Developer Division at Microsoft, has announced the productization of F#.


Значение слоава "productization" от меня ускальзает. Это значит, что интеграция войдет в поставку студии? Или речь идет о том, что им банально дадут больше бабок?

В общем, в чем новость я так и не могу понять.
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: F# - A Functional Programming Language
От: VladD2 Российская Империя www.nemerle.org
Дата: 20.10.07 07:34
Оценка:
Здравствуйте, G2, Вы писали:

G2>Что — то тогда долго они его интегрировали в VS.


Интеграция есть давно. Просто она... ну, говоря скромно, не очень хорошего качества.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: F# - A Functional Programming Language
От: VladD2 Российская Империя www.nemerle.org
Дата: 20.10.07 07:34
Оценка:
Здравствуйте, Schade, Вы писали:

S>Эта как раз-таки свежая. Раньше развитием языка занимался фактически один человек, теперь MS решила повернуться к нему если не лицом, то уж хотя бы не задом, и предоставить больше ресурсов для развития (хотя, конечно, в мэйнстрим ему не попасть).


Им и раньше не один человек занимался. К тому же эти люди были очень близки с реальными разработчиками из МС, напиример, с разработчиками из команды Шарпа. Вот только из тройки языков: Scala, Nemerle и F# последний является самым не проходным.

S>Кстати, F# здорово изменился за последнее время.


Что конкретно изменилось? И хорошо ли это?
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.