PandaPy has the speed of NumPy and the usability of Pandas (github.com)
https://github.com/firmai/pandapy
PandaPy has the speed of NumPy and the usability of Pandas (10x to 50x faster)
PandaPy has the speed of NumPy and the usability of Pandas (10x to 50x faster)
73 comments
[ 7.2 ms ] story [ 147 ms ] threadIMO Pandas documentation somehow manages to document every parameter of every method and somehow it’s almost as helpful as no documentation at all. Combined with the fact that it’s a huge package, I avoid it unless I really really need it.
A version with human-understandable docs could convince me otherwise
If you're reading this thread and wondering if it's easy to hard to use, I suggest taking a look at the docs (https://pandas.pydata.org/pandas-docs/stable/index.html) and making your own decision.
I find the combination of basic intros, user guides, and the API reference to be extremely usable and understandable; and I am reasonably sure I am human. But opinions may vary.
Want to join two dataframes together like you'd join two database tables? df.join(other=df2, on='some_column') does the wrong thing, silently, what you really wanted was df.merge(right=df2, on='some_column')
Got a list of integers that you want to put into a dataframe? pd.DataFrame({'foo': [1,2,3]}) will do what you want. What if they're optional? pd.DataFrame({'foo': [1,2,3,None]}) will silently change your integers to floating point values. Enjoy debugging your joins (sorry, merges) with large integer values.
Want to check if a dataframe is empty? Unlike lists or dicts, trying to turn a dataframe into a truth value will throw ValueError.
Simply a matter of default type of join - join defaults to left while merge defaults to inner. They use the exact same internal join logic.
>What if they're optional? pd.DataFrame({'foo': [1,2,3,None]}) will silently change your integers to floating point values.
This was a long standing issue but is no longer true.
>Want to check if a dataframe is empty? Unlike lists or dicts, trying to turn a dataframe into a truth value will throw ValueError.
Those are 1D types where that's simple to reason about. It's not as straightforward in higher dimensions (what's the truth value of a (0, N) array?), which is why .empty exists
No, join does an index merge. For example, if you try to join with string keys, it'll throw an error (because strings and numeric indexes aren't compatible).
If you try to join with numeric keys: Or even worse if your numeric values are within the range for indexes, which kind of looks right if you're not paying attention: Whereas merge does what one would expect: >> What if they're optional? pd.DataFrame({'foo': [1,2,3,None]}) will silently change your integers to floating point values.> This was a long standing issue but is no longer true.
Occurs in pandas 0.25.1 (and the release notes for 0.25.2 and 0.25.3 don't mention such a change), so that would likely be still the case in the latest stable release.
It's also a lossy conversion if the integer values are large enough: >> Want to check if a dataframe is empty? Unlike lists or dicts, trying to turn a dataframe into a truth value will throw ValueError.> Those are 1D types where that's simple to reason about. It's not as straightforward in higher dimensions (what's the truth value of a (0, N) array?), which is why .empty exists
It's not very pythonic, though. A definition of "all dimensions greater than 0" would've been much less surprising.
It was released in 0.24.0: https://pandas.pydata.org/pandas-docs/stable/user_guide/inte...
For example:
The example with the (incorrect) join above shows how even other operations can cause this type conversion.
> on : str, list of str, or array-like, optional
> Column or index level name(s) in the caller to join on the index in other, otherwise joins index-on-index.
> DataFrame.join always uses other’s index but we can use any column in df.
Interesting choices but luckily I have never been bit by this. Maybe because I first looked up on google on how to do join in pandas. Nowadays, I mostly use pd.merge though.
[1] https://pandas.pydata.org/pandas-docs/stable/reference/api/p...
One of the most difficult things about pandas is knowing how to shape your data frame before you plug it in to something. Most of my frustration comes from finding the magic incantation of symbols that will reshape my data frame the right way.
Other thing is both numpy and pandas allow for some pretty complex operations by chaining simple commands. The space of what's possible is effectively unbounded, documentation won't help there. Cookbooks cover some of the more common patterns.
Pandas is well worth it to learn however if your using python.
I've mostly use comprehensions to filter and manipulate data and I find the Panda API to be a bit clunky and esoteric.
There are nice built in functions and it displays well in a jupyter notebook but I'm not a fan of the interface.
If you don't need the advanced data manipulation capabilities of tools like pandas/dplyr (and if you're using comprehensions only, you don't), there are much easier to use options like apache nifi. Horses for courses.
It is currently sitting at the center of an ETL system at my work (not my decision) and causes headaches.
Personally, I'm an amateur at best, but Pandas has made it possible for me to do some really handy things.
Personal favorite feature: multindexing on rows AND Columns. Multiindex is such a common pattern, and so poorly handled in things like excel. Pandas really saves a lot of time with re-indexing, pivoting, stacking, or transposing data with multi indexes.
https://pandas.pydata.org/pandas-docs/stable/user_guide/inte...
I am almost repulsed by the language and now you've said it I agree wrt the documentation too.
For a more representative comparison, let's make everything 1000x larger, e.g., closing = np.concatenate(1000 * [closing])
Here's how a few representative benchmark change:
- describe: PandasPy was 5x faster, now 5x slower
- add: PandasPy was 2-3x faster than pandas, now ~15x slower
- concat: PandasPy was 25-70x faster, now 1-2x slower
- drop/rename: PandasPy is now ~1000x faster (NumPy can clearly do these operations without any data copies)
I couldn't test merge because it needs a sorted dataset, but hopefully you get the idea -- these benchmarks are meaningless, unless for some reason you only care about manipulating small datasets very quickly.
At large scale, pandas has two major advantages over NumPy/PandasPy:
- Pandas (often) uses a columnar data format, which makes it much faster to manipulate large datasets.
- Pandas has hash tables which it can rely upon for fast look-ups instead sorting.
It'd be cool if there were neutral third-parties, kind of like Jepsen, that any project could defer rigorous benchmarking to, perhaps in exchange for a flat fee (everyone pays the same fee, no matter how big or small they are).
You just can’t win.
The logic itself is easy but I'm having to step into the dark arts of DevOps and web-cancer - should be online by the summer.
"The performance claims only hold for small datasets, 1,000-100,000 numpy rows. Pandas perform better with larger data sets, the only functions that improve with a 1000x increase in size is rename, column drop, fillna mean, correlation matrix, value reads, and np calculations even out (np.log, np.exp as well as etc)"
See this thread for more on why pandas overhead adds up for real settings, and is crazy huge once you go to dask/ray/modin, and even worse, say spark: https://twitter.com/lmeyerov/status/1218093436286296069 + https://twitter.com/lmeyerov/status/1220847229537157121 . For interactive analytics apps, we want scale for bigger workloads, yet also less overhead to achieve < 100ms: ideally moving a slider will trigger lots of calcs over many widgets and their subcomponents, and the underlying stats code looks normal (e.g., df > sql > some imperative/functional lang.) Internally we write C-like buffer manips & hand-written GPU kernels & weird streaming code to achieve < 100ms wall-clock, and are trying to get tech like these up to snuff for interactive data software.
As per the JIT comment, feels like a matter of time, so happy to see this (and the pressure it creates!)
cuDF is a more plausible candidate for replacing pandas in performance-critical scenarios, and even cuDF explicitly aims to supplement pandas rather than replace it.
(Don't get me wrong. I actually appreciate the work, but also use julia)
Can anybody point me to a reasonable use case of pandas? I mean, besides printing a matrix with lines of alternating colors.
I see. For linear algebra stuff it does not offer anything essential. You rarely see a matrix as a "dataset".
Fx, joining the sum of sales by store ID from the sales table with the table of store names on the store ID. That is a major reason why people use pandas.
I gather it's very useful and extremely well loved for certain types of work though. But "the usability of Pandas" definitely doesn't ring true for me, let alone the implication that numpy is relatively unusable...if you've written lots of idiomatic Python working with its native data structures, NumPy will come very naturally, whereas Pandas is like a whole new language.
* I have to call `at` instead of using Python indexing to get a row. wat. If I try to iterate over it like "for x in df", x is a column name rather than a row. wat.
Or then, more likely, I have missed some idiomatic way to work with pandas.
You can also choose how to fill None values, namely what value you want instead. See fill_na function
Pandas is really badly designed, in the same way that most Python libraries are: each function has so many parameters. And a parameter can often be a bunch of different types. Pandas is useful, especially for time-series data, but no one particularly loves it. And, it’s embarrassingly slow. Maybe PandaPy is better, but I doubt it. When you start trying to use Python implemented functions (vs C ones) things are going to get bad no matter what you do.
Speaking of which, I decided to port over a statistical model for betting from Python to Julia week ago. I’m not done yet, and this is my first major experience with Julia, but it’s been so much nicer than using Python. The performance can easily be 10x-50x faster without really doing any extra work.
Also the language feels explicitly designed for scientific computing and really meshes well with the domain. Python the language never really was good for this, but the libraries were pretty compelling. Julia libraries have almost caught up (or in some domains, like linear algebra) have actually exceeded what’s available dor Python. Moreover, if you need to, PyCall is really easy to use.
I’m going to go out on a limb and say that people shouldn’t be using Python for new scientific computing projects. Julia has arrived, and is better in everyway (I’m still unsure about the 1-based indexing, but I’m sure I’ll get over it. 0-based waa never that great in the first place).
I am a big fan of Julia as well, and it is quite amusing to see recent growing presence of enthusiasts roaming between topics.
Reminded me of a quote that went something like "C has the low-level power of an assembly language combined with the high-level usability of an assembly language."
using Pkg; Pkd.add(“foo”)
And it works. I’m sure there’s some dependency file for projects but I don’t know how it works. Thinking about build tools and package management makes me sad, so I try and avoid it as long as possible.
Pkg.jl is based on git/github with a central registry that can I believe it's automatically updated with new packages using bots. The current version also has native supports for automatically deploying binaries and other stuff like datasets, that can be optionally loaded on demand.
Most troubles I hear is with more strict enterprise firewall scenarios and perhaps Julia JIT making it compile the libraries every time (though that's not an issue with the package manager).
Seems like it's good for creating ml models and deploying them to apple devices.