One of the faq things refers in passing to integers being 64bit instead of arbitrary precision. That's a bit more fundamental than some cpython modules don't work. Haven't found a language reference yet.
edit: it's statically typed ahead of time - that feels like something that needs a detailed description of what it's doing, given the baseline of like-python
It would cause major issues to libraries for mathematics (such as sympy or sagemath) that assume integers are arbitrary precision. Large integers are common in number theory and cryptography, where people also care very much about performance.
Their benchmarks (https://exaloop.io/benchmarks) show that Codon is much, much faster than pypy. I also just tried some microbenchmarks with their fib example (iterated many times with higher parameters) and got similar results. It's unfortunate for now that this isn't open source, but it's really valuable to demonstrate to us Python lovers what's possible using LLVM!
Their benchmarks are not to be trusted (after reading the source).
- They cheat, they rewrite code to use coden specific features to "win" (ie, parallelization and GPU optimizations)
- They don't warm up. They are simply running their competition directly rather than allowing any sort of warmup. (In other words, they are measuring cold boot and startup time)
Now, if they want to argue about startup time or whatever mattering for performance then fine. However, the representation of "20x faster!" is simply deception.
TBF, they are upfront about cheating
> Further, some of the benchmarks are identical in both Python and Codon, some are changed slightly to work with Codon's type system, and some use Codon-specific features like parallelism or GPU.
does this support any form of FFI? It'd be nice if users could shim in lightweight APIs that clone libraries like numpy/pytorch -- it'd immediately make some machine learning super portable!
The problem with these is always security updates. If you want to run on the old stuff you have to make your own security patches. Of course maybe that is exactly something that it makes sense to pay for.
It's also confusing... I mean, what does "non-production use" mean anyway? Does it mean "non-commercial use"? Or "testing/debug/staging environment"? Or "does not produce any valuable output"...?
But companies can still experiment with it without paying. IE, you can integrate it and run benchmarks to see if it would actually help your pain points.
According to this article https://perens.com/2017/02/14/bsl-1-1/ about the Business Source License, the intention conveyed by the word "production" for that license is use "in any capacity that is meant to make money".
What I want to know is: "can I add Codon to a site like https://cocalc.com that I host as long as users of Codon explicitly agree to only use it in a way that is compatible with the license?" I have absolutely no idea if that would be allowed by the rules or not.
I think that's supposed to apply to you, not your users. My understanding is that you pay if you make money using it. I can definitely see how you can easily interpret it in many other ways though.
I have not dug into the project yet,
but if it delivers on the features
it mentions it should be a game changer
for a lot of companies, heavily invested
in Python.
Surprised this sentiment is so common. It's like, do you want open source devs to work for free forever? Even Redis had to pivot to a business license.
I'm not sure what the terms are in this particular case, but in general, wanting someone to pay if they're deploying it to lots of customers seems reasonable.
On the one hand, in the same way any sort of fee (even $1) is a big impediment to adoption over free, so is the idea that "if I try this out and like it, I'll now be stuck with whatever costs they stick me with now and in the future". In a fast moving world, open source is just easier because if you change your mind, you haven't wasted money. In addition, there are only so many costs a project can afford and it is hard to know as it progresses where those will popup, so you avoid when you can.
That said, developers need to eat, and it is easy to appreciate the fact that they are letting you see the source, play with it, but pay if you want to use. I also fully support their right to license their software as they see fit.
I can swap one load balancer or cache for another. However, if my programming language has unfavourable terms I will have to rewrite all my code. Oh, and the knowledge I gained will be non transferable to another job or project because it'll always be a niche language. Better to spend the time learning how to get the same performance out of Numba or whatever other alternatives people mentioned here.
There are a lot of products released under GPL, for example, that make money for their authors. It's just that they don't make money with licensing fees.
Don't have anything significant, but giving this a quick test with some of my advent of code solutions I found it to be quite a bit slower:
time python day_2.py
________________________________________________________
Executed in 57.25 millis fish external
usr time 25.02 millis 52.00 micros 24.97 millis
sys time 25.01 millis 601.00 micros 24.41 millis
time codon run -release day_2.py
________________________________________________________
Executed in 955.58 millis fish external
usr time 923.39 millis 62.00 micros 923.33 millis
sys time 31.76 millis 685.00 micros 31.07 millis
time codon run -release day_8.py
________________________________________________________
Executed in 854.23 millis fish external
usr time 819.11 millis 78.00 micros 819.03 millis
sys time 34.67 millis 712.00 micros 33.96 millis
time python day_8.py
________________________________________________________
Executed in 55.30 millis fish external
usr time 22.59 millis 54.00 micros 22.54 millis
sys time 25.86 millis 642.00 micros 25.22 millis
It wasn't a ton of work to get running, but I had to comment out some stuff that isn't available. Some notable pain points: I couldn't import code from another file in the same directory and I couldn't do zip(*my_list) because asterisk wasn't supported in that way. I would consider revisiting it if I needed a single-file program that needs to work on someone else's machine if the compilation works as easily as the examples.
I would guess the bulk of the time is being spent in compilation. You might try "codon build -release day_2.py" then "time ./day_2" to measure just runtime.
Unfortunately stuff like this never makes it to the upstream. And i am afraid to ask why. We had pypy for years, but never got merged with python. That is why there are still minor incompatibilities between pypy and "The Python", so it's not that useful as it might have been if it got merged with cpython at some point.
I got a massive jump in performance when moving from Python 3.8 to 3.10 (over some function call optimizations I think, based on the project). And 3.11 got even better (up to 50% faster on special cases, and 10~15% on average) with respect to 3.10. Python 3.12 is already getting even more speedups and a there's a lot more down the road[0].
But Python core developers value keeping "not breaking anyones code" (Python 3 itself was a huge trip on that aspect and they're not making that mistake again), that's why things may seem slow on their end. But work is being done, and the results are there if you benchmark things.
I think 3.12 will get subinterpreters, which will allow you to have multiple interpreters, each on its own thread, sharing the process memory space. So kind of like a stopgap in between having real multithreading and pythons current situation. I'm not sure what to think of it so far, so until there's some beta or RC build to test, I don't think I'll be able to form an opinion.
There is some work to bring it up to 3.12 and some resistance to merge it into 3.X because of the impact on extension modules (they all have to be recompiled and in some cases changed a bit).
If you are interested in it, reach out to Sam. He has done a pretty impressive piece of engineering work.
While it was still on RC builds I tested it on a few projects I usually run and I got between 0 and 15% faster wrt 3.10, without any regression. But sure, every project is different and it looks like you've bumped into some with your project.
If it's not too big, you might as well just leave things as they are and wait for 3.12 to see what changes then. Apparently the changes will be bigger, so it could be be much better than 3.11 (without being much worse, hopefully!).
It's not like you can just "merge" pypy into python, they are totally different implementations. CPython is written in C and PyPy is written in RPython which is a subset of the python language that gets compiled, into into an interpreter with JIT support. You can actually write an interpreter for any language using RPython and their toolset, for example Ruby https://github.com/topazproject/topaz
Morever, a wonderful aspect of standard CPython is that you can compile it from source on a huge range of architectures in less than 5 minutes. Building Pypy from source is more difficult, and Pypy is significantly less portable (e.g., there is no viable WebAssembly version of Pypy).
No need to be afraid. The Python C extension API makes it very hard to make a JIT work well because of how it is implemented. C extensions are also part of why Python is so popular in the first place. If everybody wrote pure Python (like they write pure JavaScript), then the reference implementation would probably look like Pypy.
> "...typically on par with (and sometimes better than) that of C/C++"
What makes it faster than C++?
I see this in the documentation but I am not sure it helps me (not an expert):
> C++? Codon often generates the same code as an equivalent C or C++ program. Codon can sometimes generate better code than C/C++ compilers for a variety of reasons, such as better container implementations, the fact that Codon does not use object files and inlines all library code, or Codon-specific compiler optimizations that are not performed with C or C++.
JIT can be faster than a static compiler if it takes advantage of runtime feedback, but that's not the case here:
> While Codon does offer a JIT decorator similar to Numba's, Codon is in general an ahead-of-time compiler that compiles end-to-end programs to native code.
It can be, but if you're using PGO, the performance gains from JIT are a lot less significant and you lose the compilation overhead at runtime that you have with JIT.
Abbreviations are good to the extent that they're commonly used. It's a bit of a chicken-and-egg problem. At the time Guido picked `def`, I might have argued with him. Now, it's the standard.
If I were writing my own language, I might choose `let` instead of `def`. For example, `let x = 1`.
Can we change the title to say Python-like or something similar? Based on the comments so far, it seems that the detail that it compiles its own Python-inspired language, not actual Python, is lost on many.
The summary minimizes with "many Python programs will work with few if any modifications", but it actually looks like a substantially different language.
You convinced me to change the description of a "Python-like language" I'm working on to say "Python-like" instead of "Python": https://www.npmjs.com/package/pylang
That list actually seems genuinely pretty minimal. Reading your comment I was expecting a long major list of changes, but it's only 3 things, most of which seem relatively unlikely to impact most programs, with the possible exception of dictionary sort order.
Read the entire page. Those three bullet points aren't the extent of it. This is like the difference between Ruby and Crystal; the same syntax, similar culture, but they're fundamentally different languages.
The list of small things are for data structure. However, the language is a lot less dynamic than Python:
> Since Codon performs static type checking ahead of time, a few of Python's dynamic features are disallowed. For example, monkey patching classes at runtime (although Codon supports a form of this at compile time) or adding objects of different types to a collection.
While monkey patching is maybe not done so much in Python (outside of unit testing), adding objects of different to a collection is definitely a common operation!
From what I understand, this will be possible in the future with implicit union types. Wouldn't work with _arbitrary_ types, but with a set of types that can be computed at compile time (my guess is that this is possible in most real-world cases).
Really? The lack of Unicode strings immediately disqualifies this for most things I've worked on the last few years. No emojis, no diacritics, no non-US users. Ok for internal tools for American companies with an older workforce, I guess, but I wouldn't use this for anything that takes input from the general public (e.g., customers).
> …with the possible exception of dictionary sort order.
Which is an implementation detail that is not guaranteed by the language standard.
Porting code from 2 to 3 made me have to use a sorted dict because the code relied on the insertion order (metaclass magic operating on the class dict) but when they revamped the dictionary implementation I could do away with that fix. Until they come up with a more efficient dict and break everyone’s code again.
Does make me want to dust off the old spark parser and see what this can do with it.
That list is minimal. Elsewhere there's the no heterogenous lists and no biginteger restrictions, and it looks like import doesn't work either. Presumably no heterogenous dictionaries either - so not only unordered, but also simply typed.
> Since Codon performs static type checking ahead of time, a few of Python's dynamic features are disallowed. For example, monkey patching classes at runtime (although Codon supports a form of this at compile time) or adding objects of different types to a collection.
I can't think of a time I ever needed to do such a thing, and I've written many thousand lines of python. Python supports OOP, so classes will get you quite far in this regard.
From the README, for those who didn't scroll that far:
"While Codon supports nearly all of Python's syntax, it is not a drop-in replacement, and large codebases might require modifications to be run through the Codon compiler. For example, some of Python's modules are not yet implemented within Codon, and a few of Python's dynamic features are disallowed. The Codon compiler produces detailed error messages to help identify and resolve any incompatibilities."
The main challenge with those three issues, to me at least, is that it cannot even tell you, "yep, you need minor changes for Codon to work." It'll just work until it doesn't at runtime because your violates one of those three assumptions. So to migrate, we would have to go and figure out all the possible cases those things matter and guard against them. Not really unpalatable, just not so much a nice migration path.
Also, I'm not actually sure what they mean by internal dict sorting. Do they mean insertion order stability?
power of Python is in ecosystem of libraries, not only Python syntax.
Without the ecosystem of libraries, I am afraid use cases for Codon will be very very limited. Because Python developers (just like Node) got used to thinking: Need to do X? Lets see if I can pip install library that does it.
Ultimately, python is like super flexible glue between ecosystem of libraries that lets anyone build and prototype high quality software very quickly
The only trivial thing in software is hello world, anything more complicated or useful for end users is usually far from being trivial, in my experience.
Perhaps the way forward for Codon in terms of wider adoption would be maintaining a list of libraries that are fully Codon compatible, thereby encouraging devs to aim for cross-compatibility (which would likely naturally exclude usage of a lot of the slower Python features in turn making the libraries faster for both Codon and regular Python users)
I googled 'codon and django' and unsurprisingly found a lot of bioinformatic stuff. I tried to add language and compiler to no avail. The only query that got results was codon python compiler. Overall I think it's a name that clashes with a lot of DNA/RNA research.
While searching I found a paper from 2021 about Codon [1]. The author is not in the About page of Exaloop [2] but the supervisor of that thesis is there. From the "Future Work" section:
> we plan to add union types and inheritance. On the IR side [Intermediate Representation], we hope to develop additional builtin transformations and analyses, all the while expanding the reach of existing passes. As far as library support, we plan to port existing high-performance Python libraries like NumPy [...] to Codon; this will allow Codon to become a drop-in replacement for Python in many domains.
Having worked in the DNA analysis space and admittedly haven't read the article... my first thought was that Codon was some python library for DNA stuffs that gets compiled via LLVM for performance.
Here is the quote of the thing you are referring to:
> Codon currently uses ASCII strings unlike Python's unicode strings.
Note the word "currently." Implementing this while also tracking the constantly evolving Python language through its various versions is a lot of work. They apparently prioritizing other things over this particular aspect.
Since Codon performs static type checking ahead of time, a few of Python's dynamic features are disallowed. For example, monkey patching classes at runtime (although Codon supports a form of this at compile time) or adding objects of different types to a collection.
This seems like a very different language from Python if it won't let you do:
Yeah, that's a better way of putting it :) 90% of the time, I'm something like Sequence[T], but I'm sure I've used Sequence[Optional[T]] a couple of times. I mean, I could drive donuts in the Piggly Wiggly parking lot at 3a, I just don't, and the same for heterogenous lists.
I’ll second that. I’ve been doing python for a while and haven’t used the mixed type list. I’ve actively avoided doing something like that. The situation doesn’t come up often.
I mean, it depends on what you mean by “type”. A list of some Protocol type (what other languages call “interfaces”) is still a homogenous list even though the concrete types are heterogeneous. This is almost always what you want when you’re thinking of “a heterogeneous list”.
I just use an extension wrapper around boost::property_tree for my json (and xml) needs. Way faster than the built in json support and does automagic type conversion so I don’t have to worry about it.
Now, I’m not running at Web Scale™ but pure python was slow enough to be annoying.
Mixing types in an array/list is not remotely stupid. How exactly would you suggest expressing the lack of a value in a series of numbers without None/null? There's your mixed types.
Don't let weird dogma get in the way of practicality.
That is merely a detail of how the typing module has decided to set up convenient aliases. Treated by the language (and likely compilers) as different types.
Very interesting--Codon can generate standalone executables, object files, and LLVM IR [1]. It has strong typing for functions and argument return values [2]. Syntax looks more compact than Cython.
> The mypyc implementation and documentation live in the mypyc subdirectory of the mypy repository.
> Since mypyc uses mypy for type checking, it's convenient to use a single repository for both.
> Note that the mypyc issue tracker lives in this repository! Please don't file mypyc issues in the mypy issue tracker.
This gives the same feeling as AssemblyScript: it says it is one language, up to the point it isn't. That may make it easier for some people, but feels so uncertain. Both have a very slim set of articles in place of a proper manual; they lean on their parent languages.
Would it be possible to write performance-sensitive parts of a Python system in Codon and link that to a CPython or PyPy runtime that supports more dynamic features?
Cython takes python-ish code and compiles it to C for use as CPython C extensions. This compiles directly to machine code without the need for CPython, as far as I can tell.
183 comments
[ 2.7 ms ] story [ 257 ms ] threadedit: it's statically typed ahead of time - that feels like something that needs a detailed description of what it's doing, given the baseline of like-python
- They cheat, they rewrite code to use coden specific features to "win" (ie, parallelization and GPU optimizations)
- They don't warm up. They are simply running their competition directly rather than allowing any sort of warmup. (In other words, they are measuring cold boot and startup time)
Now, if they want to argue about startup time or whatever mattering for performance then fine. However, the representation of "20x faster!" is simply deception.
TBF, they are upfront about cheating
> Further, some of the benchmarks are identical in both Python and Codon, some are changed slightly to work with Codon's type system, and some use Codon-specific features like parallelism or GPU.
”company” is not a particularly well-defined term.
I'll note that that's the definition of "commercial".
Paying to use it seems fair.
I'm not sure what the terms are in this particular case, but in general, wanting someone to pay if they're deploying it to lots of customers seems reasonable.
On the one hand, in the same way any sort of fee (even $1) is a big impediment to adoption over free, so is the idea that "if I try this out and like it, I'll now be stuck with whatever costs they stick me with now and in the future". In a fast moving world, open source is just easier because if you change your mind, you haven't wasted money. In addition, there are only so many costs a project can afford and it is hard to know as it progresses where those will popup, so you avoid when you can.
That said, developers need to eat, and it is easy to appreciate the fact that they are letting you see the source, play with it, but pay if you want to use. I also fully support their right to license their software as they see fit.
I agree that the devs of these tools need to be paid, but that particular avenue presents some roadblocks.
By the way, Redis is still BSD licensed.
Wrong, Redis has a BSD-3 license: https://github.com/redis/redis
Optional add-ons to Redis may have non-free licenses.
[0] https://martin.ankerl.com/2019/04/01/hashmap-benchmarks-01-o...
But Python core developers value keeping "not breaking anyones code" (Python 3 itself was a huge trip on that aspect and they're not making that mistake again), that's why things may seem slow on their end. But work is being done, and the results are there if you benchmark things.
[0] See https://github.com/faster-cpython/ideas/blob/main/FasterCPyt... however that's over a year old already and I'm sure I've read/heard more specifics
There is some work to bring it up to 3.12 and some resistance to merge it into 3.X because of the impact on extension modules (they all have to be recompiled and in some cases changed a bit).
If you are interested in it, reach out to Sam. He has done a pretty impressive piece of engineering work.
https://ltworf.github.io/typedload/performance.html
If it's not too big, you might as well just leave things as they are and wait for 3.12 to see what changes then. Apparently the changes will be bigger, so it could be be much better than 3.11 (without being much worse, hopefully!).
https://bugs.debian.org/cgi-bin/pkgreport.cgi?tag=python3.9&...
There's also Nuitka as yet another alternative.
Or you're going to use a "Python-like" compiled language, consider using Nim.
What makes it faster than C++?
I see this in the documentation but I am not sure it helps me (not an expert):
> C++? Codon often generates the same code as an equivalent C or C++ program. Codon can sometimes generate better code than C/C++ compilers for a variety of reasons, such as better container implementations, the fact that Codon does not use object files and inlines all library code, or Codon-specific compiler optimizations that are not performed with C or C++.
> While Codon does offer a JIT decorator similar to Numba's, Codon is in general an ahead-of-time compiler that compiles end-to-end programs to native code.
If I were writing my own language, I might choose `let` instead of `def`. For example, `let x = 1`.
EDIT: A list of differences here: https://docs.exaloop.io/codon/general/differences
The summary minimizes with "many Python programs will work with few if any modifications", but it actually looks like a substantially different language.
> Since Codon performs static type checking ahead of time, a few of Python's dynamic features are disallowed. For example, monkey patching classes at runtime (although Codon supports a form of this at compile time) or adding objects of different types to a collection.
While monkey patching is maybe not done so much in Python (outside of unit testing), adding objects of different to a collection is definitely a common operation!
Which is an implementation detail that is not guaranteed by the language standard.
Porting code from 2 to 3 made me have to use a sorted dict because the code relied on the insertion order (metaclass magic operating on the class dict) but when they revamped the dictionary implementation I could do away with that fix. Until they come up with a more efficient dict and break everyone’s code again.
Does make me want to dust off the old spark parser and see what this can do with it.
This may or may not be the biggest concerns.
So, I think this might qualify as much as a python implementation as PyPy.
"While Codon supports nearly all of Python's syntax, it is not a drop-in replacement, and large codebases might require modifications to be run through the Codon compiler. For example, some of Python's modules are not yet implemented within Codon, and a few of Python's dynamic features are disallowed. The Codon compiler produces detailed error messages to help identify and resolve any incompatibilities."
Also, I'm not actually sure what they mean by internal dict sorting. Do they mean insertion order stability?
https://github.com/py2many/py2many/blob/main/doc/langspec.md
Would be great if all the authors of "python-like" languages get together and come up with a couple of specs.
I say a couple, because there are ones that support the python runtime (such as cython) and the ones which don't (like py2many).
Without the ecosystem of libraries, I am afraid use cases for Codon will be very very limited. Because Python developers (just like Node) got used to thinking: Need to do X? Lets see if I can pip install library that does it.
Ultimately, python is like super flexible glue between ecosystem of libraries that lets anyone build and prototype high quality software very quickly
Sort of a graalvm for python?
A quick search leads to pywasm and it is even native python. But is it usable? Any other options?
https://github.com/wasmerio/wasmer-python
Further down:
Codon is a Python-compatible language, and many Python programs will work with few if any modifications:
While searching I found a paper from 2021 about Codon [1]. The author is not in the About page of Exaloop [2] but the supervisor of that thesis is there. From the "Future Work" section:
> we plan to add union types and inheritance. On the IR side [Intermediate Representation], we hope to develop additional builtin transformations and analyses, all the while expanding the reach of existing passes. As far as library support, we plan to port existing high-performance Python libraries like NumPy [...] to Codon; this will allow Codon to become a drop-in replacement for Python in many domains.
Maybe they already did.
[1] Codon: A Framework for Pythonic Domain-Specific Languages by Gabriel L. Ramirez https://dspace.mit.edu/bitstream/handle/1721.1/139336/Ramire...
[2] https://exaloop.io/about.html
> Codon currently uses ASCII strings unlike Python's unicode strings.
Note the word "currently." Implementing this while also tracking the constantly evolving Python language through its various versions is a lot of work. They apparently prioritizing other things over this particular aspect.
This seems like a very different language from Python if it won't let you do:
In fact it's why in python they even have the | operator between types nowadays.
Now, I’m not running at Web Scale™ but pure python was slow enough to be annoying.
Not surprised but I did want to confirm.
Don't let weird dogma get in the way of practicality.
Otherwise you tag your data so that it's an array of objects.
Looking forward to giving Codon a try!
[1]: https://docs.exaloop.io/codon/general/intro
[2]: https://docs.exaloop.io/codon/language/functions
[0]: https://github.com/mypyc/mypyc
See https://github.com/mypyc/mypyc/blob/master/show_me_the_code....
https://cython.org/
?
Would it be possible to write performance-sensitive parts of a Python system in Codon and link that to a CPython or PyPy runtime that supports more dynamic features?