OCaml

Zoldar256
Unregistered
 
Post: #1
I have always loved ML. And have used SML-NJ quite a lot. But i never considered it as a replacement for the tried and true C++. But then I found Ocaml. A ML derivative, compiles to native code with great performance (People generally claim performance is faster to no more than 10% slower than equivalent C code), and has objects too. Plus it can interface with C code easily enough if needed.

Now I'm real tempted to drop C++ (Except for when I really really can't get by without it) and do my game/engine coding in Ocaml.

Anybody have experience with OCaml? I haven't tried making any games with ML, or any app over 600 lines (Which is a lot in a functional language) so I'm curious what results anybody has had for games.
Quote this message in a reply
Member
Posts: 304
Joined: 2002.04
Post: #2
all of Abuse's scripting was written with Lisp. Abuse is now opensource (and there is a OS X version) so you can look at the code.

<http://www.labyrinth.net.au/~trandor/abuse/>

if you download just the app - you can "show package contents" from finder and you can look through the lisp folder to see the code.
Quote this message in a reply
Member
Posts: 304
Joined: 2002.04
Post: #3
Zoldar256 -

sorry - when I saw ML I thought you were talking about a variant of Lisp - Ive never heard of Meta Language before. Sorry for veering off-topic.
Quote this message in a reply
Zoldar256
Unregistered
 
Post: #4
hehe. No problem.
That is interesting though. Kinda surprised Lisp was used, but it looks like Lisp worked great for the job.
Quote this message in a reply
Luminary
Posts: 5,143
Joined: 2002.04
Post: #5
Whilst we're sort of on the subject, Jak and Daxter was mostly written in a LISP variant...
Quote this message in a reply
Member
Posts: 304
Joined: 2002.04
Post: #6
Quote:Originally posted by OneSadCookie
Whilst we're sort of on the subject, Jak and Daxter was mostly written in a LISP variant...


yes! They talk about it in their postmortem <http://www.gamasutra.com/features/200207...te_pfv.htm> (free-registration required). Its an interesting read on pros and cons of using your own scripting language.

"5. GOAL rules! Practically all of the run-time code (approximately half a million lines of source code) was written in GOAL (Game Object Assembly Lisp), Naughty Dog's own internally developed language, which was based on the Lisp programming language. Before you dismiss us as crazy, consider the many advantages of having a custom compiler."

... and then later ...

"What Went Wrong
1. GOAL sucks! While it's true that GOAL gave us many advantages, GOAL caused us a lot of grief." ...

But anyway - you can always write your engine in C/C++ and use whatever scripting/functional/interpreted/whatever language for the game logic. Whatever you feel like you can code the fastest and cleanest in.
Quote this message in a reply
Member
Posts: 304
Joined: 2002.04
Post: #7
could you explain what you like about functional programming? Ive read a bit on Haskel, but was unable to grok what the advantage is.

cheers
Quote this message in a reply
Quicksilver
Unregistered
 
Post: #8
Quote:Originally posted by codemattic
Ive read a bit on Haskel, but was unable to grok what the advantage is.


I see someone has read a certain good book Cool
Quote this message in a reply
Zoldar256
Unregistered
 
Post: #9
There are several things I like about functional languages and more specifically ML.

The biggest is I find most algorithms can be expressed more naturally in a functional language. Especially those that involve some kind of recursive structure like binary trees. This generally results in significantly less code you have to write.

For instance adding one to each element in a list:
Functional:
Code:
addOne [] = []
            head :: tail = head + 1 :: addOne tail

Procedural (C++):
Code:
void addOne(std::vector<int>& array)
{
    for(std::vector<int>::iterator i = array.begin();
         i != array.end();
         ++i)
        *i = *i + 1;
}

You can imagine if your intent was to add any given value to a each element of a tree. The procedural one would get significantly more complicated, but the functional one (At least in ML with recursive data types) would only be 2 or 3 lines longer.


Another interesting feature is that functions are first class variables. Just like ints and floats. This is closely related to the concept of a closure. A closure is loosely defined as "The function that results from applying a given environment to a function". This closeure can be assigned to a variable and results in a new function.

Back to the adding to the list example:
Code:
let rec addToList num lst =
  match lst with
  [] -> []
  | head :: tail -> (head + num) :: addToList num tail;;

let addOne = addToList 1;;

Now addOne is the function that represents what addToList will do when given 1 as the first argument and whatever addOne is given as the second argument.

This presents a different, albeit less obvious way of doing object oriented programming.

Which can be a problem since I have been trained for software design using a Java or C++ style language. Objects Objects Objects. Closures is not tossed around in software design very often.

ML is also strongly typed. All variables are type checked at compile time. Kinda the philosophy of: If the types are guaranteed to be correct then the code is correct and won't crash. Less debugging time, more strict compilers.

Some things don't apply well to recursive style programming however. Like threads, and simple for loops. Objects are also tricky business with closures flying about and strong type checking.

Anyways, I have just come to the conclusion that I should just try it out. Best way to learn is through experience right?

(PS. All of this was written very quickly... So I might be wrong on some of the fine points.)
Quote this message in a reply
Luminary
Posts: 5,143
Joined: 2002.04
Post: #10
Just to point out that closures aren't restricted to functional languages. Plenty of procedural scripting languages (for example Ruby) support them.

I think most of the other points were subjective, though there are definitely benefits to a type system which guarantees you'll never segfault or bus-error Smile
Quote this message in a reply
Zoldar256
Unregistered
 
Post: #11
I didn't know Ruby had closures...

And of course it's all subjective. But I'm bored from too much C++ so I'll take any type of opinion ;-)
Quote this message in a reply
M.J.
Unregistered
 
Post: #12
Quote:Originally posted by Zoldar256
For instance adding one to each element in a list:
Functional:
Code:
addOne [] = []
            head :: tail = head + 1 :: addOne tail

Procedural (C++):
Code:
void addOne(std::vector<int>& array)
{
    for(std::vector<int>::iterator i = array.begin();
         i != array.end();
         ++i)
        *i = *i + 1;
}

If you only only want to count lines of code, I can do that in one line in C++:

Code:
transform(array.begin(), array.end(), array.begin(), bind2nd(plus<int>(), 1));
Grin
Seriously though, this isn't a lines-of-code contest. My experience with functional languages is minimal at best (very basic experimentation with Haskell), but I can see many advantages. As a "math" guy the declarative nature of functional languages really appeals to me. I'd love to implement some real-world problem in a functional language to see for myself the advantages/disadvantages over C++ (the procedural language I work in most often), but I don't think I can convince the guys at work to go for that.

And here's why... when I think about it, very little of my time is spent defining algorithms, or even debugging algorithms. When I think about this, the benefits of a function language start to fade. How is a functional language going to help me interface with a SQL database better? How is it going to help me create a GUI? How is it going to help me parse text files better? These are the questions that keep me from even trying to justify using a functional language for tasks at work. I guess my programming tasks boil down to "can I access the libraries I need" more than "how clean, clear, and theoretically beautiful is the syntax of the language". And, for good or bad, the libraries follow the programming herds and the herds use C++.

I know I can probably call C/C++ code from most functional language, but my previous experience on cross-language apps tells me that passing any kind of semi-complicated data structure across the language boundary eats up a lot of programming and debugging time all by itself. Does this negate any advantage of going with the functional language in the first place? I guess, like Zoldar256, I'll just have to do some experimentation to find out.
Quote this message in a reply
Zoldar256
Unregistered
 
Post: #13
hehe. Yes well, I really should avoid the "lines of code" argument. It has no real merit. But you got what I was going for. Some things just make more sense implemented functionally.

As for accessing external libraries. Making bindings has been a huge pain in the a** for a lot of non-C languages. Sometimes their niceties don't translate well into the low level. Luckily I haven't found to many issues with OCaml.
Ocaml can output standard C style object files. And there is only a few extra steps to call OCaml functions from C.

Quote: And here's why... when I think about it, very little of my time is spent defining algorithms, or even debugging algorithms. When I think about this, the benefits of a function language start to fade.

Interesting... I think all my time is defining interfaces, the underlying design and algorithms. All of these have changing design goals. So the ability to rapidly change the algorithm and experiment and how the various components of the software relate to eachother is essential in my opinion.

Quote:How is a functional language going to help me interface with a SQL database better? How is it going to help me create a GUI? How is it going to help me parse text files better?

I dunno about interfacing with a SQL database.. But create GUI's again have treelike structures for the hierarchy of elements, lists and other standard software design patterns. So really if the pattern applies well to a functional language it would help. I know many times while coding MVC style UI's I'd like to use closures to replace simple delegate classes.

While GUI's are questionable on which one is better. Parsing text files? Ah easy, functional. BNF or whatever your favorite grammar language is very reminiscent of a functional language. So I think parsing is much more natural with a functional language.

Though IMHO. Lex and Yacc have really made this a non-issue regardless of target programming language.
Quote this message in a reply
M.J.
Unregistered
 
Post: #14
Quote: So really if the pattern applies well to a functional language it would help. I know many times while coding MVC style UI's I'd like to use closures to replace simple delegate classes.


In the various discussions of functional languages around on the net, "closures" often come up. Despite reading numerous definitions and examples, I'm still not sure I know what they are. Are they something more than idea of "first class" functions? In other words, functions that can be returned from other functions, passed as arguments to other functions, stored in variables, etc?

Quote:While GUI's are questionable on which one is better. Parsing text files? Ah easy, functional. BNF or whatever your favorite grammar language is very reminiscent of a functional language. So I think parsing is much more natural with a functional language.

Though IMHO. Lex and Yacc have really made this a non-issue regardless of target programming language.


I think I overstated my text file usage. "Parsing" is probably too strong a word. "File I/O" would have better described what I was trying to say, usually it just involves reading tables of data into data structures, processing the data structures, and outputting the processed data back to a file. Though, maybe, if I took the time to formalize it a bit more, I could get by with using more reusable code (like that created via Lex/Yacc) instead of starting from scratch for each new task. Something to keep in mind.

What I was really getting at though, is that it seems to me that the examples lying around for how great such-and-such functional language is usually involve things like calculating Fibonacci numbers, or factorials, or something where the concept is very well matched to a functional style. But this sort of core, "math-like" functionality is where I spend very little time of my programming/debugging time. Most of it is on interfacing with external libraries (database access, networking, etc) or some sort of user interaction (input files, GUI displays, etc.). If we're in a MVC world, functional languages seem to me to fit the model part, but not so much the controller part where I seem to spend most of my time.

Maybe I'm unusual in this way, but I don't think so. Admittedly if I were to read intros to C++ programming on the web with the same level of familiarity (or lack thereof) that I have with OCaml, I'd probably have the same complaint ("OK, great, I can output 'Hello world!', but how does that help me write a real program!?!?").

Anyway, this discussion has convinced me to try out OCaml. I'm downloading it right now (found an OS X how-to and installer here, for anyone reading along at home). So you may have a convert on your hands. I can come to you with all my questions, right? Smile
Quote this message in a reply
Zoldar256
Unregistered
 
Post: #15
Quote:In the various discussions of functional languages around on the net, "closures" often come up. Despite reading numerous definitions and examples, I'm still not sure I know what they are. Are they something more than idea of "first class" functions? In other words, functions that can be returned from other functions, passed as arguments to other functions, stored in variables, etc?

A closure a function with the environment at the time of it's creation applied. An environment in this case is all the variables currently in scope and their values.

Using a bad example. Take this function
Code:
float power(float x,unsigned int y)
{
    if(y == 0)
        return 1.0;
    return x*power(x, y-1);
}

the closure of applying the environment equivalent to assigning x the value of 4.0. IE, the first argument is 4.0. Is equivlent to:
Code:
float power4(unsigned int y)
{
    if(y == 0)
        return 1.0;
    return 4.0*power4(y-1);
}

So I suppose closures are kinda like functions that represent the partial evaluation of another function.
Sorry about my bad explanation, hope you get the idea tho.

Quote: What I was really getting at though, is that it seems to me that the examples lying around for how great such-and-such functional language is usually involve things like calculating Fibonacci numbers, or factorials, or something where the concept is very well matched to a functional style.

Exactly why I started this thread. Aside from some very specific applications (Compilers, parsers theorom provers) I have seen very little "real-world" applications done in a functional language.

Ocaml taunted me however since a lot of the FAQ's seemed to claim that it was good for "real-world" applications. There's even a web browser written in OCaml. Some guy also wrote an OpenGL fps in Ocaml for a class. Not very real world. But I never saw anybody say, "Hey here's my FPS written in SML/Haskell/Rex!"

And that's what got me thinking.
Quote:If we're in a MVC world, functional languages seem to me to fit the model part, but not so much the controller part where I seem to spend most of my time.

Yea... they do only seem well applied to the model part.
After using Cocoa I can't imagine doing the controller&view in anything else anyways. Grin

Quote:Anyway, this discussion has convinced me to try out OCaml. I'm downloading it right now (found an OS X how-to and installer here, for anyone reading along at home). So you may have a convert on your hands. I can come to you with all my questions, right?
Blink Rasp
Uh oh.... hehe. I never said I was "good" at OCaml Grin
But I'd love to hear how it goes!

Note: OCaml can also be installed using Fink.
Quote this message in a reply
Post Reply 

Possibly Related Threads...
Thread: Author Replies: Views: Last Post
  checkers code written in OCAML? ab44045 1 3,434 Jun 5, 2005 04:55 AM
Last Post: socksy