Monte Carlo 3x Speedup
Hey all, I've been experimenting with Mojo for some simple RL and wrote a blog post about it. Thought it might be interesting to share here!
https://open.substack.com/pub/alexinch/p/reinforcing-learning-using-mojo-to
Reinforcing Learning: Using Mojo🔥 to learn 3x faster
Rewriting a Monte Carlo RL approach in Mojo for a 3x speed increase, with some drawbacks...
12 Replies
Thank you for taking the time. Good stuff.
@Aloysius Aloysius, I checked the bug reports and did not see one for round(). Would you like to create one or if you prefer I would be willing?
Hi, I'm out and about right now - if you have the time please feel free to create a report, otherwise I can do this evening!
I'll do it
(Turns out I stepped in it, lol, still working on it)
With this commit they added the ability to round FloatLiterals so it works in nightly but it's still waiting on all the conformances to work so that all the declared Int and Floats work correctly
Could you elaborate a bit on what exactly “you don’t get” regarding
var
Yeah sure, it made sense to me when there were let and var declarations. Now that everything uses var, why not just add it implicitly? Seems closer to Python and I don't see the downside
I think
looks better than
and it lets you set variable types without initializing
There are many reasons i can think of
- Mojo has different scoping rules than Python, declaration is indeed different from assignment.
- You can shadow names in small scopes like loop body, if branches, etc.
- A variable in Mojo has to be defined and initialised on every path even if it's never used.
- We don't want Python's ugly
global
and nonlocal
So it's really, for many usecases (like scripting), we can rely on the compiler to add them for us (we have that in def
s), but for system programming purposes, the markers are necessary. Python's semantics is tailed to the fact that it's a dynamically typed scripting language. Consider the following Python program:
where expr
is a vey complex expression that can be prove to be always true, but not constant folded into true.
It's a valid program in Python, because we won't run into problems at runtime, we can simply say that a
is defined in the function scope, and call it a day. In Mojo, however, it's very difficult to argue that a
is defined only in the true branch in a program like
but not the above. We need the var
keyword to indicate the scope explicitly:
VS
In summary, Python can't warn you of this problem, and the programer can get this right most of the time, so the rules are very relaxed. But in a compiled language, the compiler have to get this correct every single time, so it needs more information and more precise scoping (you see this in pyright as well)
If you still find difficult to see the neccecity of some kind of marker, look no further than python's own dataclass declaration: Python works just fine with good old classes and naked attribute assignment like self.a = a
in __init__
. But if you want type checking, you will have to list everything in the class definition itself beforehand.I guess sora likes var 😉
I’m actually pretty against the removal of
let
.Thanks for the extensive reply! I can see the benefits of var for clarity. I do still kind of think implicitly handling is ok: like if your example was:
But I can see how that's less clear. My comment was an observation from early use, no doubt I'll get used to it.
In fact that in
def
s, it is inferred to match python behaviour.
Now there is no way to define something like, for there is no way to distinguish explicit typing and variable declaration
To make my position very clear: I agree with you that if we can find a good set of implicit rules, it will look way nicer. In fact, Guido himself joined this server and proposed the same thing (a: T
instead of var a: T
) to Chris. It's just that being a system programming language closes many doors.I agree with this, i like enforced immutability at runtime