English | 中文版
[TOC]
Redis's SORT command can sort the elements stored in a list, set, or sorted set key.
typedef struct _redisSortObject {
robj *obj; /* the value from the key being sorted */
union {
double score; /* used when sorting by numeric value */
robj *cmpobj; /* used when sorting string values with BY option */
} u;
} redisSortObject;Sorting a key that contains numeric values:
SORT <key>When the server executes SORT numbers, it performs the following steps:
- Allocate an array with the same length as the
numberslist; each element of the array is aredisSortObject. - Iterate the array and point each element's
objto the corresponding entry in thenumberslist, establishing a one-to-one mapping. - Convert each object pointed to by
objinto adoubleand store that value into the corresponding element'su.scorefield. - Sort the array by the numeric
u.scorevalues in ascending order. - Iterate the array and return the objects pointed to by each
objas the sorted result to the client.
Using the ALPHA option lets SORT order elements as strings:
SORT <key> ALPHAWhen the server executes SORT xx ALPHA, it performs:
- Allocate an array of
redisSortObjectwhose length equals the size of thexxcollection. - Iterate the array and point each element's
objto the corresponding member of thexxcollection. - Sort the array by the string values of the elements pointed to by
obj(ascending lexicographic order). - Iterate the array and return each element referenced by
objto the client in order.
By default SORT performs ascending order; ASC explicitly requests ascending order (the two commands below are equivalent):
SORT <key>
SORT <key> ASCUse DESC to request descending order:
SORT <key> DESCBy default SORT uses the elements in the input key as the sorting weight. With the BY option you can specify an external field pattern to be used as weights:
SORT xx BY xxxExample:
MSET apple-price 8 banana-price 5.5 cherry-price 7
SORT fruits BY *-priceWhen the server executes SORT xx BY xxx, it performs:
- Allocate an array of
redisSortObjectwith length equal to the size ofxx. - Iterate the array and point each element's
objto the corresponding member ofxx. - For each element, using the
objand theBYpatternxxx, look up the corresponding weight key. - Convert each weight value to a
doubleand store it into the element'su.score. - Sort the array by
u.scorein ascending order. - Iterate the sorted array and return the elements referenced by
objto the client.
BY assumes weight keys contain numeric values; when weight keys store strings use ALPHA together with BY:
SORT xx BY xxx ALPHAExample:
SADD fruits "apple" "banana" "cherry"
MSET apple-id "FRUIT-25" banana-id "FRUIT-79" cherry-id "FRUIT-13"
SORT fruits BY *-id ALPHAWhen the server executes SORT xx BY xxx ALPHA, it performs:
- Allocate an array of
redisSortObjectwhose length equals the size offruits. - Point each array element's
objto the corresponding element offruits. - For each element, using the
objand theBYpatternxxx, find the corresponding weight key. - Set each element's
u.cmpobjto point to the weight object's value. - Sort the array by the string values of the referenced weight objects.
- Iterate the array and return the elements referenced by
objto the client.
LIMIT restricts the returned portion of the sorted elements. Format:
LIMIT <offset> <count>offset: number of sorted elements to skip.count: number of elements to return after skippingoffsetelements.
Example:
SADD alphabet a b c d e f
SORT alphabet ALPHA LIMIT 2 3When the server executes SORT xx ALPHA LIMIT m n, it performs:
- Allocate an array of
redisSortObjectwith length equal to the size ofxx. - Point each
objto the corresponding element inalphabet. - Sort the array by string values.
- Move the pointer to index
mand return the elements atxx[m],xx[m+1], ..., up to the requestedcountto the client.
GET lets SORT return values from external keys based on the sorted elements and the provided pattern:
SORT xx ALPHA GET xxxWhen the server executes SORT xx ALPHA GET xxx, it performs:
- Allocate an array of
redisSortObjectsized toxx. - Point each
objto the corresponding element inxx. - Sort the array by string values.
- For each sorted element, use the
GETpattern to look up the requested keys. - Return the found keys' values to the client in the order specified by the
GETpatterns.
STORE persists the sorted result into the specified key so it can be reused later. Format:
SORT xx ALPHA STORE xxxWhen the server executes SORT xx ALPHA STORE xxx, it performs:
- Allocate an array of
redisSortObjectsized toxx. - Point each
objto the corresponding element inxx. - Sort the array by string values.
- If the
xxxkey exists, delete it. - Create
xxxas an empty list. - Push the sorted elements into the tail of the
xxxlist. - Return the elements to the client.
Execution of a SORT command proceeds in the following phases:
-
Sorting
The server sorts using
ALPHA,ASC/DESC, andBYoptions to generate an ordered result set. -
Limiting the result set
LIMITis applied to restrict the size of the result set. -
Fetching external keys
GETpatterns are used to retrieve external keys for each element, producing the final result set. -
Storing the result
STOREwrites the result set to the specified key. -
Returning to the client
The server iterates the final result set and sends it back to the client.
Example:
SORT <key> ALPHA DESC BY <by-pattern> LIMIT <offset> <count> GET <get-pattern> STORE <store_key>Steps:
SORT <key> ALPHA DESC BY <by-pattern>
LIMIT <offset> <count>
GET <get-pattern>
STORE <store_key>Except for GET, the textual placement of options in the command does not affect the execution order of the options.
Example:
SORT <key> ALPHA DESC BY <by-pattern> LIMIT <offset> <count> GET <get-pattern> STORE <store_key>is equivalent to
SORT <key> LIMIT <offset> <count> BY <by-pattern> ALPHA GET <get-pattern> STORE <store_key> DESCIf multiple GET options are present, their relative order must be preserved when reordering options; otherwise the resulting output will change.
Example:
SORT <key> GET <pattern-a> GET <pattern-b> STORE <store_key>is not equivalent to
SORT <key> STORE <store_key> GET <pattern-b> GET <pattern-a>[1] Huang Jianhong. Redis Design and Implementation