
Writing a Faster Sorting Algorithm - zefei
https://probablydance.com/2016/12/27/i-wrote-a-faster-sorting-algorithm/
======
tener
Neat algorithm, but it is largely comparing apples to oranges. std::sort is
universal, ska_sort is not:

> Another problem is that I’m not sure what to do for data that I can’t sort.
> For example this algorithm can not sort a vector of std::sets

> Another problem is that right now there can only be one sorting behavior per
> type. You have to provide me with a sort key, and if you provide me with an
> integer, I will sort your data in increasing order. If you wanted it in
> decreasing order, there is currently no easy interface to do that.

Useful algorithm, but we already knew there are faster algorithms if we
introduce additional requirements!

~~~
willtim
With some generic programming, even complex data can be radix sorted in linear
time. Google the Discriminator papers of Fritz Henglein.

~~~
eternalban
[http://www.diku.dk/hjemmesider/ansatte/henglein/papers/hengl...](http://www.diku.dk/hjemmesider/ansatte/henglein/papers/henglein2008.pdf)

[http://www.diku.dk/hjemmesider/ansatte/henglein/papers/hengl...](http://www.diku.dk/hjemmesider/ansatte/henglein/papers/henglein2010.pdf)

[https://pdfs.semanticscholar.org/f425/7af9221ca7fe21dc84a049...](https://pdfs.semanticscholar.org/f425/7af9221ca7fe21dc84a049a8545a28a874ae.pdf)

------
Animats
This is a classic. In fact it's close to the first algorithm ever patented -
SyncSort, patented in 1971. Still being developed and sold, SyncSort remains
the leading technology for big sorts.[1] When you need to sort a few
terabytes, they have a product for that. It's a radix sort with self-adjusting
bucket boundaries. So it can deal with keys that are not well distributed.

[1]
[http://www.syncsort.com/en/Products/Sort](http://www.syncsort.com/en/Products/Sort)

------
necessity
Can't test the code as there are numerous compilation errors with my version
of gcc and libc++. Besides what others have written, the author seems to have
taken only one measurement for each case. And more importantly there is no
mention of randomization at all. If he sorted all input sizes using algorithm
A and then all input sizes using algorithm B (instead of doing it in random
order) it is possible that there is bias in the measurements (due to cache,
branch prediction, etc), specially if he used the same input, just varying the
size. I'm also worried about what he used to measure time, as he mentions that
for a small number of elements it takes a few microseconds (gettimeofday(3)
has a resolution of 1 microsecond, so the measured time is dangerously close
to the clock resolution - clock_gettime(3) should be use instead if available,
having a resolution of 1ns - or the C++ equivalent for nanosecond precision).
Making the algorithm code available is not enough, it is just as important
(perhaps even more) to make the benchmark code available. The "tests and
benchmarks" code available on Github is a .hpp unfit for reproduction. I want
to see the raw data used in the plots and the code to generate it, and I want
to be able to run it myself. Otherwise there's no reason to trust it.

------
testerofwaters
It might just be faster because the author is comparing their hybrid radix
sort implementation to std::sort (which is comparison-based).

Would be more valid to compare to Boost's "spreadsort" which is similarly a
hybrid radix sort algorithm (and also outperforms std::sort).

~~~
imaginenore
Why doesn't the STL switch to the hybrid sorting approach?

~~~
adrianN
AFAIK the STL is free to use any algorithm they want as long as it's O(n log
n).

~~~
niftich
This is correct. The C++ standard specifies that sort must have a big-O
complexity of n log(n). This can be seen on pdf page 925 of this working draft
from 2014 [1].

[1] [http://www.open-
std.org/jtc1/sc22/wg21/docs/papers/2014/n429...](http://www.open-
std.org/jtc1/sc22/wg21/docs/papers/2014/n4296.pdf)

~~~
sqeaky
So providing a faster sort would be a violation?

The standard doesn't seem to say "or better" here, but I know that in other
places it does (or least used to say something similar).

~~~
wnesensohn
No, f = O(n log n) means that f doesn't grow significantly faster than n log
n. That is true for f = n log n, but it's also true for f = n. The "or better"
is implicit by using big-O.

Note that this wouldn't be true if the standard said that it has to be Θ(n log
n).

------
ryao
Just to share since it is related, you can sort faster than a naive O(nlogn)
algorithm whenever data is in the form of partitions where the partitions are
sorted, but the contents of each partition are not. i.e. The largest element
in each partition is smaller than the smallest in the next partition.

There the total number of elements are n and the average size of a partition
is m. Then you need only apply any O(log(m)) algorithm to each partition to
sort everything. That multiplies the time complexity by n/m. Then substitute n
= m^c and the sort becomes O(n/c*log(n)) time. That gives you a factor of c
speed up on what would otherwise be an O(nlogn) operation.

This trick is usable when you want to sort a B-Tree like structure where the
data in each node is unsorted, but the nodes themselves are sorted. The file
system hierarchy on a machine is like that. The default output of zfs list is
also like that.

------
amelius
Every sort algorithm should take locality of data-access into account. Without
this, a comparison to other algorithms may not be fair.

~~~
AndrewOMartin
Why pick this one detail to account for, and not one of the infinity of other
details that may be relevant in certain circumstances?

------
web007
> This is a trivial function which is less complicated than the comparison
> operator that you would have to write for std::sort.

Unless it uses the same interface (aka call a comparator for each eval) it's
apples to oranges. I also didn't see comparisons vs swaps enumerated, which
matter for complex data structures or complex comparators.

------
armamut
I'd be happy to see, how well it would behave compared to the famous Timsort
([https://en.wikipedia.org/wiki/Timsort](https://en.wikipedia.org/wiki/Timsort)).

------
Pica_soO
Watching std:sort in sort sound- i can only wonder, why this second fine
granular sorting pass, long after you pushed out the first sorting part out of
cache?

