zset alpha sort, and sort order

701 views
Skip to first unread message

Wayne Larsen

unread,
Oct 28, 2009, 3:38:59 PM10/28/09
to Redis DB
With the new sorted sets:
"The score value can be the string representation of a double
precision floating point number"

Does this mean only numbers are allowed for sorting? Is there going to
be an option to sort lexicographically, as there is now with the sort
command?

Also, is there documentation on the collation order? I found CouchDB's
View Collation page[1] to be quite helpful when working with it. I
tried a similar script[2] and found the results somewhat different. Is
this the canonical result?

!"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]
^_`abcdefghijklmnopqrstuvwxyz{|}~


[1] http://wiki.apache.org/couchdb/View_collation
[2] http://gist.github.com/220749

Thanks,
Wayne

Salvatore Sanfilippo

unread,
Oct 28, 2009, 5:29:04 PM10/28/09
to redi...@googlegroups.com
On Wed, Oct 28, 2009 at 8:38 PM, Wayne Larsen <wayne...@gmail.com> wrote:
>
> With the new sorted sets:
> "The score value can be the string representation of a double
> precision floating point number"

Hello Larsen,

yep, but actually as you'll see in a moment sorted sets are more
powerful than that.

> Does this mean only numbers are allowed for sorting? Is there going to
> be an option to sort lexicographically, as there is now with the sort
> command?

I implemented something that helped to guaranteed the O(log(N)) update
operation and at the same time it's a very interesting feature of
Redis sorted tests I think: entries with the same score are ordered
lexicographically:

$ ./redis-cli zadd myset 1 foo
1
$ ./redis-cli zadd myset 1 bar
1
$ ./redis-cli zadd myset 1 how
1
$ ./redis-cli zadd myset 1 are
1
$ ./redis-cli zadd myset 1 you
1
$ ./redis-cli zadd myset 1 fine
1
$ ./redis-cli zrange myset 0 -1
1. are
2. bar
3. fine
4. foo
5. how
6. you
$

Where is the downside? Just one, you can't use ZRANGEBYSCORE.

What if you want to use ZRANGEBYSCORE with lexicographically order?
You have to turn the lexicographically order into a number, but
because double floats are only 8 bytes of data, there is a limit, you
can only sort by the first N-digits of a word.

How to turn a word into a score?

For instance, if you want to use the first four letters to produce the
score, this is the rule:

score = first-byte-value*(256^3) + second-byte-value*(256^2) +
third-byte-value*(256^1) + fourth-byte-value

Just omit from the sum non existing chars if the word is < 4 chars in length.

Why this works? You are just considering the bytes as digits of a
radis-256 number :)
Note that even if you are sorting just for the first four letters, the
sorted set will be *fully* sorted, because who gets the same score
will get sorted anyway lexicographically. Just your ranges are limited
to four digits ranges, for instance from "foob" to "fooc".

> Also, is there documentation on the collation order? I found CouchDB's
> View Collation page[1] to be quite helpful when working with it. I
> tried a similar script[2] and found the results somewhat different. Is
> this the canonical result?
>
> !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]
> ^_`abcdefghijklmnopqrstuvwxyz{|}~

Redis SORT uses strcoll() so sorting collation is done accordingly to
the locale collation set in the system. Sorted sets are using plain
strcmp() currently, but this is going to be strcoll() too before Redis
1.1 release.

Cheers,
Salvatore

--
Salvatore 'antirez' Sanfilippo
http://invece.org

"Once you have something that grows faster than education grows,
you’re always going to get a pop culture.", Alan Kay

Wayne Larsen

unread,
Oct 28, 2009, 6:23:09 PM10/28/09
to Redis DB


On Oct 28, 3:29 pm, Salvatore Sanfilippo <anti...@gmail.com> wrote:
> On Wed, Oct 28, 2009 at 8:38 PM, Wayne Larsen <waynelar...@gmail.com> wrote:
>
> What if you want to use ZRANGEBYSCORE with lexicographically order?
> You have to turn the lexicographically order into a number, but
> because double floats are only 8 bytes of data, there is a limit, you
> can only sort by the first N-digits of a word.

Okay, that makes sense. I started looking at redis because I wanted a
low level tool to manage some indexes that I would have full control
over, so I guess I shouldn't be surprised if that's exactly what redis
is... :)

Thanks for redis.
Wayne

Carlo Pires

unread,
Dec 22, 2011, 1:05:16 PM12/22/11
to redi...@googlegroups.com
This post really should be in documentation of sorted sets.
Reply all
Reply to author
Forward
0 new messages