Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
ruanhaishen
redis
Commits
9212eafd
Commit
9212eafd
authored
Mar 04, 2010
by
Pieter Noordhuis
Browse files
implemented ZREMBYRANK
parent
94e543b5
Changes
2
Hide whitespace changes
Inline
Side-by-side
redis.c
View file @
9212eafd
...
@@ -661,6 +661,7 @@ static void brpopCommand(redisClient *c);
...
@@ -661,6 +661,7 @@ static void brpopCommand(redisClient *c);
static
void
appendCommand
(
redisClient
*
c
);
static
void
appendCommand
(
redisClient
*
c
);
static
void
substrCommand
(
redisClient
*
c
);
static
void
substrCommand
(
redisClient
*
c
);
static
void
zrankCommand
(
redisClient
*
c
);
static
void
zrankCommand
(
redisClient
*
c
);
static
void
zremrangebyrankCommand
(
redisClient
*
c
);
/*================================= Globals ================================= */
/*================================= Globals ================================= */
...
@@ -708,6 +709,7 @@ static struct redisCommand cmdTable[] = {
...
@@ -708,6 +709,7 @@ static struct redisCommand cmdTable[] = {
{
"zincrby"
,
zincrbyCommand
,
4
,
REDIS_CMD_BULK
|
REDIS_CMD_DENYOOM
,
1
,
1
,
1
},
{
"zincrby"
,
zincrbyCommand
,
4
,
REDIS_CMD_BULK
|
REDIS_CMD_DENYOOM
,
1
,
1
,
1
},
{
"zrem"
,
zremCommand
,
3
,
REDIS_CMD_BULK
,
1
,
1
,
1
},
{
"zrem"
,
zremCommand
,
3
,
REDIS_CMD_BULK
,
1
,
1
,
1
},
{
"zremrangebyscore"
,
zremrangebyscoreCommand
,
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zremrangebyscore"
,
zremrangebyscoreCommand
,
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zremrangebyrank"
,
zremrangebyrankCommand
,
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zrange"
,
zrangeCommand
,
-
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zrange"
,
zrangeCommand
,
-
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zrangebyscore"
,
zrangebyscoreCommand
,
-
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zrangebyscore"
,
zrangebyscoreCommand
,
-
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zcount"
,
zcountCommand
,
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
{
"zcount"
,
zcountCommand
,
4
,
REDIS_CMD_INLINE
,
1
,
1
,
1
},
...
@@ -5052,6 +5054,61 @@ static unsigned long zslDeleteRange(zskiplist *zsl, double min, double max, dict
...
@@ -5052,6 +5054,61 @@ static unsigned long zslDeleteRange(zskiplist *zsl, double min, double max, dict
return
removed
;
/* not found */
return
removed
;
/* not found */
}
}
/* Delete all the elements with rank between start and end from the skiplist.
* Start and end are inclusive. */
static
unsigned
long
zslDeleteRangeByRank
(
zskiplist
*
zsl
,
unsigned
int
start
,
unsigned
int
end
,
dict
*
dict
)
{
zskiplistNode
*
update
[
ZSKIPLIST_MAXLEVEL
],
*
x
;
unsigned
long
traversed
=
0
,
removed
=
0
;
int
i
;
/* start and end are given 0-based, but zsl uses 1-based
* ranks internally */
start
++
;
end
++
;
x
=
zsl
->
header
;
for
(
i
=
zsl
->
level
-
1
;
i
>=
0
;
i
--
)
{
while
(
x
->
forward
[
i
]
&&
(
traversed
+
(
i
>
0
?
x
->
span
[
i
-
1
]
:
1
))
<
start
)
{
traversed
+=
i
>
0
?
x
->
span
[
i
-
1
]
:
1
;
x
=
x
->
forward
[
i
];
}
update
[
i
]
=
x
;
}
traversed
++
;
x
=
x
->
forward
[
0
];
while
(
x
&&
traversed
<=
end
)
{
zskiplistNode
*
next
;
for
(
i
=
0
;
i
<
zsl
->
level
;
i
++
)
{
if
(
update
[
i
]
->
forward
[
i
]
==
x
)
{
if
(
i
>
0
)
{
update
[
i
]
->
span
[
i
-
1
]
+=
x
->
span
[
i
-
1
]
-
1
;
}
update
[
i
]
->
forward
[
i
]
=
x
->
forward
[
i
];
}
else
{
/* invariant: i > 0, because update[0]->forward[0]
* is always equal to x */
update
[
i
]
->
span
[
i
-
1
]
-=
1
;
}
}
if
(
x
->
forward
[
0
])
{
x
->
forward
[
0
]
->
backward
=
x
->
backward
;
}
else
{
zsl
->
tail
=
x
->
backward
;
}
next
=
x
->
forward
[
0
];
dictDelete
(
dict
,
x
->
obj
);
zslFreeNode
(
x
);
while
(
zsl
->
level
>
1
&&
zsl
->
header
->
forward
[
zsl
->
level
-
1
]
==
NULL
)
zsl
->
level
--
;
zsl
->
length
--
;
removed
++
;
traversed
++
;
x
=
next
;
}
return
removed
;
}
/* Find the first node having a score equal or greater than the specified one.
/* Find the first node having a score equal or greater than the specified one.
* Returns NULL if there is no match. */
* Returns NULL if there is no match. */
static
zskiplistNode
*
zslFirstWithScore
(
zskiplist
*
zsl
,
double
score
)
{
static
zskiplistNode
*
zslFirstWithScore
(
zskiplist
*
zsl
,
double
score
)
{
...
@@ -5271,6 +5328,45 @@ static void zremrangebyscoreCommand(redisClient *c) {
...
@@ -5271,6 +5328,45 @@ static void zremrangebyscoreCommand(redisClient *c) {
}
}
}
}
static
void
zremrangebyrankCommand
(
redisClient
*
c
)
{
int
start
=
atoi
(
c
->
argv
[
2
]
->
ptr
);
int
end
=
atoi
(
c
->
argv
[
3
]
->
ptr
);
robj
*
zsetobj
;
zset
*
zs
;
zsetobj
=
lookupKeyWrite
(
c
->
db
,
c
->
argv
[
1
]);
if
(
zsetobj
==
NULL
)
{
addReply
(
c
,
shared
.
czero
);
}
else
{
if
(
zsetobj
->
type
!=
REDIS_ZSET
)
{
addReply
(
c
,
shared
.
wrongtypeerr
);
return
;
}
zs
=
zsetobj
->
ptr
;
int
llen
=
zs
->
zsl
->
length
;
long
deleted
;
/* convert negative indexes */
if
(
start
<
0
)
start
=
llen
+
start
;
if
(
end
<
0
)
end
=
llen
+
end
;
if
(
start
<
0
)
start
=
0
;
if
(
end
<
0
)
end
=
0
;
/* indexes sanity checks */
if
(
start
>
end
||
start
>=
llen
)
{
addReply
(
c
,
shared
.
czero
);
return
;
}
if
(
end
>=
llen
)
end
=
llen
-
1
;
deleted
=
zslDeleteRangeByRank
(
zs
->
zsl
,
start
,
end
,
zs
->
dict
);
if
(
htNeedsResize
(
zs
->
dict
))
dictResize
(
zs
->
dict
);
server
.
dirty
+=
deleted
;
addReplyLong
(
c
,
deleted
);
}
}
static
void
zrangeGenericCommand
(
redisClient
*
c
,
int
reverse
)
{
static
void
zrangeGenericCommand
(
redisClient
*
c
,
int
reverse
)
{
robj
*
o
;
robj
*
o
;
int
start
=
atoi
(
c
->
argv
[
2
]
->
ptr
);
int
start
=
atoi
(
c
->
argv
[
2
]
->
ptr
);
...
...
test-redis.tcl
View file @
9212eafd
...
@@ -1442,7 +1442,7 @@ proc main {server port} {
...
@@ -1442,7 +1442,7 @@ proc main {server port} {
$r zrangebyscore zset 20 50 LIMIT 2 3 withscores
$r zrangebyscore zset 20 50 LIMIT 2 3 withscores
}
{
d 40 e 50
}
}
{
d 40 e 50
}
test
{
ZREMRANGE basics
}
{
test
{
ZREMRANGE
BYSCORE
basics
}
{
$r del zset
$r del zset
$r zadd zset 1 a
$r zadd zset 1 a
$r zadd zset 2 b
$r zadd zset 2 b
...
@@ -1452,7 +1452,7 @@ proc main {server port} {
...
@@ -1452,7 +1452,7 @@ proc main {server port} {
list
[
$r
zremrangebyscore zset 2 4
]
[
$r
zrange zset 0 -1
]
list
[
$r
zremrangebyscore zset 2 4
]
[
$r
zrange zset 0 -1
]
}
{
3
{
a e
}}
}
{
3
{
a e
}}
test
{
ZREMRANGE from -inf to +inf
}
{
test
{
ZREMRANGE
BYSCORE
from -inf to +inf
}
{
$r del zset
$r del zset
$r zadd zset 1 a
$r zadd zset 1 a
$r zadd zset 2 b
$r zadd zset 2 b
...
@@ -1462,6 +1462,16 @@ proc main {server port} {
...
@@ -1462,6 +1462,16 @@ proc main {server port} {
list
[
$r
zremrangebyscore zset -inf +inf
]
[
$r
zrange zset 0 -1
]
list
[
$r
zremrangebyscore zset -inf +inf
]
[
$r
zrange zset 0 -1
]
}
{
5
{}}
}
{
5
{}}
test
{
ZREMRANGEBYRANK basics
}
{
$r del zset
$r zadd zset 1 a
$r zadd zset 2 b
$r zadd zset 3 c
$r zadd zset 4 d
$r zadd zset 5 e
list
[
$r
zremrangebyrank zset 1 3
]
[
$r
zrange zset 0 -1
]
}
{
3
{
a e
}}
test
{
SORT against sorted sets
}
{
test
{
SORT against sorted sets
}
{
$r del zset
$r del zset
$r zadd zset 1 a
$r zadd zset 1 a
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment