<hey_guys>
Hey all, quick question: is there a way to refer to a signature defined in an .mli file the same way you might refer to code in code.ml using the module name Code?
hey_guys has quit [Ping timeout: 246 seconds]
mcclurmc has quit [Ping timeout: 272 seconds]
sh0t has quit [Ping timeout: 265 seconds]
hey_guys has joined #ocaml
hey_guys has quit [Client Quit]
waneck has joined #ocaml
emanuelz has joined #ocaml
emanuelz has quit [Quit: emanuelz]
hey_guys has joined #ocaml
struktured has joined #ocaml
hey_guys has quit [Client Quit]
mcclurmc has joined #ocaml
mcclurmc has quit [Remote host closed the connection]
mcclurmc has quit [Remote host closed the connection]
idegen has quit [Quit: Leaving.]
tamago_ has joined #ocaml
mcclurmc has joined #ocaml
<tamago_>
Can someone help me with OCaml idioms?
obadz- has quit [Ping timeout: 252 seconds]
<tamago_>
I've learned that I can avoid using the object system in favor of modules.
<tamago_>
Let's say I'm trying to do something basic that I would do with objects.
mcclurmc has quit [Ping timeout: 276 seconds]
<tamago_>
Maybe I should just completely refactor my design, but imagine I have something like this:
<tamago_>
module M = struct let x = ref 5 let set_x new_x = x := new_x let get_x = x end;;
<tamago_>
Then elsewhere I want to create multiple instances of that object.
<tamago_>
Or module rather.
<tamago_>
Is there an idiomatic way of doing this? Should I be using a functor? It seems rather elaborate.
mcclurmc has joined #ocaml
obadz has joined #ocaml
<dmbaturin>
tamago_: You don't store anything (mutable or not) within modules.
<dmbaturin>
You define a type and a bunch of functions that work with that type, possibly including a function that creates values of that type (analogous to constructor in OO).
<dmbaturin>
If you want to protect some invariants, you make the type abstract (don't specify its implementation in the signature) so only functions from your module and nothing else can work with that type.
jabesed has quit [Ping timeout: 246 seconds]
<tamago_>
I can do that in the .mli I believe.
Axle has joined #ocaml
Axle has quit [Client Quit]
<tamago_>
I feel this is a lot like making everything a static function in Java, which makes me uncomfortable...
<dmbaturin>
* forgot the exception in the signature, but you see the point
<tamago_>
yea thanks!
<tamago_>
Oh, but assuming you are only making one module with the PERSON sig, would it be better to have a person.ml file and a person.mli (and thus never use the word module explicitly)?
<dmbaturin>
If it's not nested, in real programs .ml/.mli pair is usually a better choice indeed.
<tamago_>
cool.
seanmcl has quit [Quit: My MacBook Pro has gone to sleep. ZZZzzz…]
<dmbaturin>
Static methods in Java do feel odd, methods are supposed to be about changing object state rather than doing things to values from outside world and returning them back.
<tamago_>
Yea, but modules seem to be designed to do exactly that.
<tamago_>
Note: this feels more natural in a functional context than in Java.
<dmbaturin>
But there is nothing in Java that you can use as a container for functions, so class misuse is the only thing to do if a collection of functions is what you want.
<tamago_>
I see, using static methods pays the overhead for objects and then doesn't use it.
<tamago_>
Thanks for the help. It's easy to write OCaml but hard to write it well coming from Java since there are so many choices.
<tamago_>
Java always has just one choice, even if it isn't really appropriate.
mcclurmc has quit [Ping timeout: 255 seconds]
darkf_ has joined #ocaml
darkf has quit [Ping timeout: 248 seconds]
BitPuffin|osx has quit [Ping timeout: 246 seconds]
ggole has joined #ocaml
darkf_ is now known as darkf
obadz has quit [Ping timeout: 252 seconds]
obadz has joined #ocaml
<dmbaturin>
tamago_: By the way, what's going on with Swing? Are they seriously going to kill it off in favor of JavaFX? How's it confirmed to the Swing API?
<tamago_>
I'm not sure, I haven't worked with Swing.
<dmbaturin>
* compared
<tamago_>
My Java development has all been with Google App Engine.
<dmbaturin>
Ah, ok. I haven't written any Java in a long time so I'm wondering what's going on there.
<tamago_>
(mostly)
<tamago_>
Java 8 introduces a ton of new features.
<tamago_>
But I haven't used it yet.
<tamago_>
Java adding more functional features.
<tamago_>
Sort of redundant as long as Scala exists though.
<dmbaturin>
Yeah, I've heard. Without good support for handling immutable values it's not very functional though. As far as I understand there're still no actual higher-order functions either.
milosn has quit [Ping timeout: 256 seconds]
milosn has joined #ocaml
struktured has quit [Ping timeout: 246 seconds]
keen___________4 has joined #ocaml
keen___________3 has quit [Ping timeout: 252 seconds]
moei has quit [Quit: Leaving...]
obadz has quit [Ping timeout: 256 seconds]
obadz has joined #ocaml
mcclurmc has joined #ocaml
Algebr has joined #ocaml
mcclurmc has quit [Ping timeout: 250 seconds]
swgillespie has joined #ocaml
Simn has joined #ocaml
tamago_ has quit [Quit: Page closed]
swgillespie has quit [Quit: My MacBook Pro has gone to sleep. ZZZzzz…]
johnf_ has joined #ocaml
johnf__ has quit [Read error: Connection reset by peer]
Sim_n has joined #ocaml
fantasticsid has joined #ocaml
Simn has quit [Ping timeout: 252 seconds]
johnf_ has quit [Read error: Connection timed out]
johnf_ has joined #ocaml
fantasticsid has quit [Read error: Connection reset by peer]
fantasticsid has joined #ocaml
badon has joined #ocaml
tmtwd has quit [Read error: Connection reset by peer]
slash^ has joined #ocaml
tmtwd has joined #ocaml
mcclurmc has joined #ocaml
jeffmo has joined #ocaml
mcclurmc has quit [Ping timeout: 264 seconds]
moei has joined #ocaml
badon has quit [Ping timeout: 248 seconds]
tamago has joined #ocaml
<tamago>
Gah, programming in OCaml is like writing with my left hand. Why didn't I start with OCaml and learn things right from the start?
tamago has quit [Client Quit]
<adrien>
that's actually a fairly nice analogy :p
<Algebr>
Is ocamlnet's netstring still the best game in town for parsing html?
<Algebr>
okay apparently cow also has a HTML module with a of_string function
mcclurmc has joined #ocaml
amnn has joined #ocaml
amnn has quit [Client Quit]
<flux>
cow?
mcclurmc has quit [Ping timeout: 246 seconds]
<flux>
oh, there's a library called cow :)
<flux>
thought it was an acronym
<flux>
algebr, does it work?-)
slash^ has quit [Quit: Leaving.]
<Algebr>
I'm getting to it
dmiles_akf has quit []
dmiles_afk has joined #ocaml
<Algebr>
well, it crapped out already. It crapped out on <!DOCTYPE html>, the very first line.
<Algebr>
I suspect its built on top of ocamlnet's netstring, the api is similar..
IMM has joined #ocaml
IMM has quit [Client Quit]
Onemorenickname has joined #ocaml
<Onemorenickname>
Hi guys
<Onemorenickname>
Do you know an online IDE for ocaml ?
<Algebr>
To explore the language or to actually do work?
<flux>
algebr, well, it doesn't depend on netstring. I suppose it's possible the code base is just copied from there, but I wonder why would someone have bothered :)
Haudegen has quit [Ping timeout: 272 seconds]
<Onemorenickname>
Algebr, to explore the language
<Onemorenickname>
I just want to try some inversion counting stuff
<Onemorenickname>
In fact, I will have exams like really soon
<Onemorenickname>
And it's in ocaml
<Onemorenickname>
(It's very basic stuff)
<Onemorenickname>
But I'd like to train a lil' bit
<Algebr>
flux: its really painful that an HTML parser craps out on <!DOCTYPE html>, something that hmm, every single page has
<adrien>
well, there have been a few questions about that recently and I think it makes sense to put the most beginner-friendly in the topic
<Drup>
iocaml is more suited for interactive tutorials, since you can have pre-loaded code
jave has joined #ocaml
<Drup>
adrien: yeah, but the jsoo ones has much more ponies^W syntactic coloration.
<adrien>
:)
<Onemorenickname>
ponies ?
<Drup>
Onemorenickname: he has a bit of an obsession, just roll with it
<Onemorenickname>
I see
<adrien>
Drup: bunnies actually
<adrien>
ponies is simply because it's the internet currencty
<adrien>
currency*
<adrien>
Drup: try.ocamlpro.com loads *much* more quickly however
<Onemorenickname>
how can i make a balanced tree from a binary tree ?
<Drup>
adrien: the camlp4 effect
yomimono has quit [Ping timeout: 248 seconds]
<adrien>
Drup: well, one freezes my web browser for a bit and the other doesn't so I guess I'll put try.ocamlpro.com even though it doesn't have colors
<Drup>
Onemorenickname: that's more of an algorithmic question, there are plenty of very pedagogic answers on the web.
<Onemorenickname>
Drup : I see
octachron has quit [Ping timeout: 264 seconds]
<Onemorenickname>
Can I paste you a code, and one of you tells me how I can improve it so it looks better in ocaml ?
<Drup>
Sure, use pastebin
<Onemorenickname>
(It's already written in ocaml, and it works)
<Drup>
merge sort on arrays, hum, this is not very functional :3
<Onemorenickname>
I don't know which nlog(n) sort is functional ^^'
<Onemorenickname>
So I made the quickiest one
<Drup>
merge sort is functional, it's just better on lists
<Onemorenickname>
how do you fold a list in two ?
<ggole>
The first function could just be Array.iteri (Printf.printf "%d : %d") a
<Drup>
fold a list in two ?
<Onemorenickname>
I dont' know what's the right word in english
<Onemorenickname>
From a list, making two lists of equal lengths
<Drup>
you don't need to do that
<Onemorenickname>
?
<Drup>
you don't mutate the list
<Drup>
so no need to copy it
<Onemorenickname>
how do you sort then ?
<Drup>
It's exactly the same algorithm
<Onemorenickname>
the one I know is making two sub arrays
<Drup>
just that, instead of copying around all the time, it creates new lists
<Onemorenickname>
sorting them, and merging them
<Onemorenickname>
The list only contains references ?
<Drup>
No
<Drup>
Onemorenickname: I advise you to try to separate the algorithm in 3 phase (clearly define each by a function): split, sort (the recursive call), merge
<Onemorenickname>
so, when you split
<Onemorenickname>
oh, you delete the old list ?
<Drup>
well, not really, you don't take care of it :)
<Drup>
if it's not used anymore, the GC will take care of it
<Onemorenickname>
I don't see how it is different than with arrays then
<Drup>
Try to write it, you'll see you can express it in a much more functional style.
<Onemorenickname>
I think it's because I don't know what a functional style is
idegen has joined #ocaml
octachron has joined #ocaml
<Onemorenickname>
Drup : I edited a lil' bit the code I've written before, in order to compare with a defined function
<Onemorenickname>
But I get an error and I don't understand where it comes from
<struktured>
Onemorenickname: its a a relatively new generic syntax extension framework for ocaml that allows you to extend the AST...for example,to derive common traits like show,compare,etc, use ppx_deriving: https://github.com/whitequark/ppx_deriving
mcclurmc has joined #ocaml
<Onemorenickname>
struktured, what is the AST ?
<Onemorenickname>
I'm new to ocaml
<Onemorenickname>
I was wondering too, how do you guys use ocaml ?
mcclurmc has quit [Ping timeout: 256 seconds]
creichert has joined #ocaml
dhil has quit [Ping timeout: 256 seconds]
<struktured>
Onemorenickname: abstract syntax tree.. the compiler has a phase which it turns the code into a tree like structure, ppx allows a developer to inject stuff into the tree at certain eXtension Points
<Onemorenickname>
oh i see
<Onemorenickname>
i didnt know
<Onemorenickname>
sounds cool
<Onemorenickname>
so you can add your own stuff to ocaml ?
<struktured>
Onemorenickname: it's almost like AOP or bytecode weaving, or code generation
<struktured>
hence drup called it metaprogramming
<Onemorenickname>
oh, i thought you were really touching the parser
<Onemorenickname>
but, it's the same at the end
<Onemorenickname>
I think I'd love to build my own interpreter
<struktured>
It is, I guess, it touches the AST. I am only describing it in terms of other techniques to express it's usefulness
<Onemorenickname>
I think I will do it once I finish my exams
<Onemorenickname>
OH, I understand
<Drup>
Onemorenickname: basically, you insert your onw AST to AST transformation, before the compiler does anything
<Drup>
just after parsing
<Onemorenickname>
Drup : That's what I understood
<Onemorenickname>
And it makes me want to create my own language
<ollehar>
I mean, it's just php if you don't use type hints, right?
<theblatte>
yes, it leaves <?php alone and untyped, but <?hh //strict has to be typed
<ollehar>
yeah
<ollehar>
(btw, you know what "blatte" means in swedish? oO)
<theblatte>
(blue or red?)
<ollehar>
so I want my colleagues to be more type-safe, but without forcing hacklang upon them
<ollehar>
myself, I'd love to use hacklang
<ollehar>
but architecture, blah blah blah
<Drup>
but, facebook is using it :D
<Drup>
(also, I don't think you need to type the whole file, don't you ?)
<theblatte>
Drup: you need to give type hints to all your functions
<Drup>
hum, ok
<theblatte>
if you don't that's fine too, but you won't get any guarantees
<theblatte>
ollehar: I see what you mean, and the answer is that there is not such static analyzer right now. Of course typing the whole of php is impossible without hints, but maybe you can type the easy bits without going insane
<theblatte>
with type inference I mean
<theblatte>
the question is whether that would cover a pratically significant portion of the code you write
<ollehar>
yeah, some basic stuff would be interesting to do
<ollehar>
good point
<theblatte>
and whether there is value in typing only parts of your code
<Drup>
theblatte: how much of facebook's php code is covered with typing now ?
<ollehar>
wait, if you don't use // strict, you can type-hint parts of it?
<theblatte>
<?hh defaults to // partial and accepts any (or almost iirc) <?php code
<ollehar>
(and how f-cking awesome it is that one of the hacklang devs hang around here!!)
<theblatte>
except that you can start using hack features such as datatypes
<theblatte>
I'm not a hacklang dev :)
<ollehar>
oh
<theblatte>
but I work at fb
<ollehar>
ah
<ollehar>
with ocaml?
<theblatte>
yes
<theblatte>
on static analysis :)
<ollehar>
infer?
<theblatte>
yes :D
<ollehar>
+1
<theblatte>
Drup: We have deployed Hack at Facebook and it has been a great success. Over the last year, we have migrated nearly our entire PHP codebase to Hack, thanks to both organic adoption and a number of homegrown refactoring tools.
walter|r has quit [Remote host closed the connection]
<ollehar>
didn't fb make a program to check types in javascript?
<Drup>
interesting
<theblatte>
ollehar: yes, that's flow
<theblatte>
it uses more type inference, interestingly
<theblatte>
you only have to spell out the type at module boundaries
<ollehar>
cool
ggole_ has quit []
<ollehar>
one useful thing could be to check for nulls, as in hack, but use function docs instead of type hints. also, function docs should be enforced.
<ollehar>
maybe.
<theblatte>
ollehar: so yeah, maybe you can convince your colleagues that it's ok for you to write types and they don't have to unless they want to change your code
<ollehar>
as in "@return string|null@
<ollehar>
-"
<theblatte>
and sneakily convert more and more of the codebase to hack
<ollehar>
theblatte: yeah, but for that I have to convince the hosts guys, project leader, what have you
<theblatte>
then enjoy the better performances from hhvm since it knows the types
<ollehar>
so, politics
<theblatte>
(you guys use hhvm, right? ;)
<ollehar>
a type-inferring linter would be easier.
<ollehar>
nope, no hhvm.
<ollehar>
I could try push it more.
<ollehar>
if it works with typo3.
<ollehar>
(don't ask)
<theblatte>
(yeah, not going there)
<theblatte>
it looks like typo3 wasn't 100% compatible with hhvm a year ago
<Drup>
what is typo3 ?
<Drup>
I feel like I'm going to be horrified, but my curiosity is too strong
<theblatte>
Drup: it's still time not to learn anything about it
<Drup>
Go on, I'm ready.
mcclurmc has joined #ocaml
<theblatte>
it's a cms
<Drup>
for now, I see nothing terrifying.
<theblatte>
ah
<theblatte>
my bad
<theblatte>
well I've used it at a university and it was a very unpleasant experience
<Drup>
^^'
slash^ has quit [Read error: Connection reset by peer]
<ollehar>
it's the qurkiest piece of software ever invented.
<ollehar>
they made their own configuration language called typoscript
johnf_ has quit [Read error: Connection reset by peer]
<ollehar>
parsed with regexp, I would assume, no lexer or stuff
<ollehar>
the template engine, fluid, is also parsed with regexp.
mcclurmc has quit [Ping timeout: 265 seconds]
<ollehar>
it's only big here in germany, basically.
<Drup>
=')
<ollehar>
very easy to make sql injection by mistake in typoscript
<ollehar>
also, some horryfying security bug were discovered in an earlier version, due to messy function signatures.
<ollehar>
one function could return 100, 200, false and something else
<ollehar>
and then later, "if return_value > 100, let the user in"
<ollehar>
but 200 is "not authorized"
<ollehar>
stuff like that
lobo has joined #ocaml
<ollehar>
I could go on
<Drup>
That is quite amazing
<ollehar>
still, typo3 is ok compared to the replacement framework started 10 years ago: neos.
<ollehar>
oh well
<ollehar>
we'll see what will happen
Hannibal_Smith has quit [Quit: Leaving]
<ollehar>
anyway, I should read the code to flow et al
<ollehar>
I could just steal the parser/lexer/ast from hacklang and then make my own evals, no?
<theblatte>
hack and flow actually share some infrastructure too
<theblatte>
all the stuff that makes them paralellisable basically
<ollehar>
hm ok
<SomeDamnBody>
I want to create an array of references...
<SomeDamnBody>
I need to know how to tell ocaml that I want just a uninitialized reference...
<SomeDamnBody>
do I do ref 0? or ref?
<Drup>
an array of references, really ?
<flux>
ref None
<SomeDamnBody>
ah ok
<SomeDamnBody>
Drup, well right now my program is leaking like hell
<SomeDamnBody>
So I think that instead of initializing the array to contain a default item, having a reference will allow me to only allocate for what I need
<SomeDamnBody>
because tons of the memory elements just represent duplicate items
<SomeDamnBody>
I guess I could create an Array of optional you know, but...
<Drup>
No, that's not going to work as you expect it
<SomeDamnBody>
which, array of optional or array of ref?
<Drup>
both, really
<SomeDamnBody>
I'm not sure how you mean to be explaining it work work "as I expect it"
<SomeDamnBody>
can I draw out how I think it would use memory
<SomeDamnBody>
and then you clarify, that way we're certain? :)
<Drup>
sure =)
<SomeDamnBody>
Really my program is consuming so much memory that it eventually just runs out of swap and dies
<Drup>
what is your program doing ?
<SomeDamnBody>
I expect it to consume about 1.5 gigs, because that's what it really needs. Not 20 gigs
<SomeDamnBody>
Well, basically, I have a 300 mb memory dump gathered from an analysis tool
<SomeDamnBody>
I want to conservatively interpret at every byte offset what the data item could be, because we don't know which offset is correct
<SomeDamnBody>
so, that would mean about 1.2 gigs, because it's 4 * 300mb
<SomeDamnBody>
Which is fine. I don't care if I chew 2-3 gigs, I have space. It just needs to have the right complexity
<SomeDamnBody>
anyway-
<Drup>
can you show the program ?
<SomeDamnBody>
I can successfully iterate over the array I create for that and initialize them all correctly, but in converting the array to a list, it eats all the memory
<SomeDamnBody>
well, my program is part of some private code
<SomeDamnBody>
but I think that I can slice off a piece of it and show it to you. I need to pretty much excise it so that others can use it, there are quite a few moving pieces, and I will have to basically test to make sure that it compiles and all in order to show you
<SomeDamnBody>
that might take some time...
<SomeDamnBody>
can I finish the explanation so that you can tell me how I'm wrong?
<SomeDamnBody>
about how memory gets used in ocaml?
<Drup>
sure
<rgrinberg>
Drup: :D
<Drup>
rgrinberg: It's one of these patch "CI is happy, hence it's correct".
<rgrinberg>
lwt has quite a backlog with pr's
<rgrinberg>
i should learn the internals a little better to help out :/
<Drup>
I merge on the part I know, but not on the rest, and since nobody is actively working on things, it stays like that
<SomeDamnBody>
ok thanks drup
<SomeDamnBody>
anyway, I know that all arguments and names and stuff in ocaml are pass by reference
<Drup>
SomeDamnBody: if an array of int is eating your memory, I don't see how an array of ref is going to be better, on the contrary
<SomeDamnBody>
it's not an array of int
<SomeDamnBody>
it's an array of { list * int }
<SomeDamnBody>
so, that list could be empty, and the int be 0
<Drup>
and how is that better than an array of list * int ?
<Drup>
(introducing a ref)
<SomeDamnBody>
(in the default case, and the default happens a lot for our analysis data)
<SomeDamnBody>
well it's not going to be an array of list * int
<SomeDamnBody>
it's array of (list * int) ref
<SomeDamnBody>
and that ref is always one word size
<Drup>
That's my question, how is "array of (list * int) ref" better than "array of (list * int)"
<SomeDamnBody>
so, my thinking is, I'll save space by only having allocating for the times when I actually have something to put there
<Drup>
"array of (list * int)" is already an array of pointer
<SomeDamnBody>
oh I didn't know that
<SomeDamnBody>
So could I save space by having array of (list * int) option?
<Drup>
no, that would not save space
<SomeDamnBody>
ok
<SomeDamnBody>
well, I guess what I'll do is just try and slice off what I can so that I can let you look at it
<SomeDamnBody>
would it help if I were just to quickly create a gist for it?