Live data from Hacker News

Making Python faster with Rust

ohadravid.github.io

191–200 of 223 posts

Re: Making Python faster with Rust

#191
post #169

Earlier quoted context omitted.

Yeah I guess this isn't true anymore, it looks like maybe it was true in 2.6 days.

I immediately verified both claims. list(map(func, arr)) did bring 10% benefits if the func is builtin e.g. int(), str(). But if func is tuple(), list(), set() or any kind of user defined function, list(map()) is always slower. You can try yourself to see list(map()) is not working well: import numpy as np a = np.arrange(100000, 100000) %%timeit b1 = [np.sum(x) for x in a] # repeat once %%timeit b2 = list(map(np.sum,…

thanks!

Re: Making Python faster with Rust

#192
post #166

I think a big mistake in the article, in a context where performance is the main objective, is that the author uses an array of structs (AoS), rather than a struct of arrays (SoA). An SoA makes it so that the data is ordered contiguously, which is easy to read for the CPU, while an AoS structure interleaves different data (namely the x and y in this case), which is very annoying for the CPU. A CPU likes to read chunk…

Modern CPU caches are usually loaded in 64-byte units - much larger than 128 bits. I just ran some tests with a C program on an Intel I5 with both AoS and SoA using a list of 1B points with 32-bit X and Y components. Looping through the list of points and totaling all X and Y components was the same speed with either AoS or SoA. It's easy to make intuitive guesses about how things are working that seem completely rea…

It appears that you didn't enable optimizations. That's needed for SIMD, which can only be taken advantage of with contiguously packed data.

Re: Making Python faster with Rust

#193

Earlier quoted context omitted.

For research? -- Julia seems to be definitely better. It's purpose-built for doing just that. R would also be there. If you want general statistics, then add J to the fold. But specific fields often have their own, bespoke solutions. I've only ever dealt with math, but it has plenty of its own niche languages that are much better than, say, Sage. My personal choice was Maxyma, but that's because I like Common Lisp. F…

> For research? -- Julia seems to be definitely better. It's purpose-built for doing just that. What does this even mean lol, “research” is incredibly broad

I think what OP means is that Julia has a number of features that work very well for the workflows and processes of programming for scientists.

1. Interactive workflows. One of the defining features of doing science is that you don't know what the right answer or right approach is. This makes interactive workflows (like REPLs) really valuable since you can load data once and do 100 different analyses on it. Notebooks are also really useful as a means of showing both code and results at the same time, and Pluto.jl is one of the best here since it removes the possibility of ending up with inconsistent state by tracking dependencies between cells.

2. Reproducibility. Another important feature for scientific code is that you want someone to be easily able to take your data and code, be easily able to install the code, run it and get the same answer. This is one of python's biggest shortcomings. Python has an incredibly rich package ecosystem, but is lacking a good unified system for reproducibly installing packages (Poetry is the closest but it has problems with binary dependencies). Julia (and Rust) have virtual environments and the idea of a manifest file that records the exact version of all your (transitive) package dependencies built in which make it trivial for someone else with no instructions get an exact clone of all the software needed to run your code.

3. Ease of use. Most scientists are scientists first and bad to mediocre at programming (there are obviously exceptions, some scientists are great programmers). Static type systems and manual memory management are major impediments to beginner use. C++ gets some scientific use for it's performance, but there's a reason Python R and Matlab are the languages of most scientists.

4. Performance. Lots of fields (bio, astronomy, high energy physics, chemistry) need a fast language to be able to get results in a reasonable amount of time. Julia is fast and is one of the easier languages to write GPU accelerated code in.

5. Open source. Closed source languages (Matlab) are a total pain to deal with.

Re: Making Python faster with Rust

#194

Earlier quoted context omitted.

LineProfiler is the best tool to learn how to write performant Python and do code optimization. https://github.com/pyutils/line_profiler You can literally see the hot spot of your code, then you can grind different algorithms or change the whole architecture to make it faster. For example replace short for loops to list comprehensions, vectorize all numpy operations (only vectorize partially do not help the issue), u…

You should take a look at Scalene - it's even better. https://github.com/plasma-umass/scalene

Wow this looks sick! Great thanks!

Re: Making Python faster with Rust

#195
post #181

Earlier quoted context omitted.

They would have gotten the same performance in python with numpy if they did it like this instead of calling norm for every polygon centers = np.array([p.center for p in ps]) norm(centers - point, axis=1) They were just using numpy wrong. You can be slow in any language if you use the tools wrong

what is the difference? though I do feel like i see this a lot with these kinds of "we re-wrote it in rust and everything is fast". comparing to a language with gc options often the scenario on one hand, i feel like you should just learn how to use your stuff properly. on the other hand it is interesting to see that people who can't write fast code or use libraries properly are actually writing fast code. like fast c…

The first issue I have with it is that they've now convinced a large portion of people that read this article that a very good tool is not as good as it actually is. This is a disservice to the great engineering that has gone into it.

The rest of my issue with it is hypothetical. I don't care what he does at work, but I would imagine if I was that dude's manager and he convinced me that he put in all this work and determined that the best path forward is to introduce a brand new language and tool chain into our environment to maintain (obviously not as big a deal if it was already well engrained in the team), and then I come to find out that he could have gotten even better results by changing a few lines with the existing tools, that I would have to reevaluate my view of said developer.

Re: Making Python faster with Rust

#196
post #166

Earlier quoted context omitted.

Modern CPU caches are usually loaded in 64-byte units - much larger than 128 bits. I just ran some tests with a C program on an Intel I5 with both AoS and SoA using a list of 1B points with 32-bit X and Y components. Looping through the list of points and totaling all X and Y components was the same speed with either AoS or SoA. It's easy to make intuitive guesses about how things are working that seem completely rea…

It appears that you didn't enable optimizations. That's needed for SIMD, which can only be taken advantage of with contiguously packed data.

Results with -O are below.

x1 (AoS) vs x2 (SoA): no performance difference x3 (arrays not in structure, both arrays in loop): slower x4 (arrays not in structure, one array in loop): faster

My advice is still not to assume that SoA is always faster than AoS without benchmarking.

  + cc -O -o x1 x1.c
  + ./x1
  s=1808348672

  real 0m11.775s
  user 0m3.540s
  sys 0m6.592s
  + ./x1
  s=1808348672

  real 0m5.427s
  user 0m2.727s
  sys 0m2.682s
  + cc -O -o x2 x2.c
  + ./x2
  s=1808348672

  real 0m5.185s
  user 0m2.296s
  sys 0m2.872s
  + ./x2
  s=1808348672

  real 0m5.140s
  user 0m2.273s
  sys 0m2.852s
  + cc -O -o x3 x3.c
  + ./x3
  s=1808348672

  real 0m6.423s
  user 0m3.745s
  sys 0m2.660s
  + ./x3
  s=1808348672

  real 0m6.485s
  user 0m3.741s
  sys 0m2.714s
  + cc -O -o x4 x4.c
  + ./x4
  s=1808348672

  real 0m4.875s
  user 0m2.205s
  sys 0m2.651s
  + ./x4
  s=1808348672

  real 0m4.894s
  user 0m2.189s
  sys 0m2.684s

Re: Making Python faster with Rust

#197

Earlier quoted context omitted.

They would have gotten the same performance in python with numpy if they did it like this instead of calling norm for every polygon centers = np.array([p.center for p in ps]) norm(centers - point, axis=1) They were just using numpy wrong. You can be slow in any language if you use the tools wrong

You made this assertion multiple times, but so far it’s been entirely unsupported in fact, despite TFA having made the entire code set available for you to test your hypothesis on.

[flagged]

Re: Making Python faster with Rust

#198
post #119

This was a silly and unnecessary optimization. He’s just using numpy wrong. Instead of: for p in ps: norm(p.center - point) You should do: centers = np.array([p.center for p in ps]) norm(centers - point, axis=1) You’ll get your same speed up in 2 lines without introducing a new dependency

Isn't this the version of refenced on the github repo [0] which speeds up 6x instead of 101x? There's also a "v1.5" version which is 6x faster, and uses "vectorizing" (doing more of the work directly in numpy). This version is much harder to optimize further. [0] https://github.com/ohadravid/poly-match

[flagged]

Re: Making Python faster with Rust

#199
post #196

Earlier quoted context omitted.

It appears that you didn't enable optimizations. That's needed for SIMD, which can only be taken advantage of with contiguously packed data.

Results with -O are below. x1 (AoS) vs x2 (SoA): no performance difference x3 (arrays not in structure, both arrays in loop): slower x4 (arrays not in structure, one array in loop): faster My advice is still not to assume that SoA is always faster than AoS without benchmarking. + cc -O -o x1 x1.c + ./x1 s=1808348672 real 0m11.775s user 0m3.540s sys 0m6.592s + ./x1 s=1808348672 real 0m5.427s user 0m2.727s sys 0m2.682s…

The reason you're not seeing much difference is that your struct is very small, just 16 bytes. In the cases where you're using both x and y in the loop (x1 and x2), you can fit 4 of them in a cache line and you're not wasting space since you need to use both. In the case you're only using one of the values (x3), you're wasting half a cache line and that shows in the benchmark. If you had a bigger struct and/or where you're not using all the members in the calculation, you'd see a much bigger difference in performance between SoA and AoS.

Re: Making Python faster with Rust

#200
post #181

Earlier quoted context omitted.

what is the difference? though I do feel like i see this a lot with these kinds of "we re-wrote it in rust and everything is fast". comparing to a language with gc options often the scenario on one hand, i feel like you should just learn how to use your stuff properly. on the other hand it is interesting to see that people who can't write fast code or use libraries properly are actually writing fast code. like fast c…

The first issue I have with it is that they've now convinced a large portion of people that read this article that a very good tool is not as good as it actually is. This is a disservice to the great engineering that has gone into it. The rest of my issue with it is hypothetical. I don't care what he does at work, but I would imagine if I was that dude's manager and he convinced me that he put in all this work and de…

[flagged]
Post reply on HN