Empty/delete a set in Redis? - set

Maybe I'm just blind, but I don't see an explicit set command in Redis for emptying an existing set (without emptying the entire database). For the time being, I'm doing a set difference on the set with itself and storing it back into itself:
redis> SMEMBERS metasyn
1) "foo"
2) "bar"
redis> SDIFFSTORE metasyn metasyn metasyn
(integer) 0
redis> SMEMBERS metasyn
(empty list or set)
But that looks a little silly... is there a better way to do this?

You could delete the set altogether with DEL.
DEL metasyn
From redis console,
redis> SMEMBERS metasyn
1) "foo"
2) "bar"
redis> DEL metasyn
(integer) 1
redis> SMEMBERS metasyn
(empty list or set)

Related

What does it mean value "-1" of a Redis Key?

Consider a simple Redis TTL command as follows:
127.0.0.1:6379> ttl cache/employee/jackson_ray/login
(integer) -1
127.0.0.1:6379>
What does the -1 value means ?

How to get index of value if exists?

I need to store strings and associate a unique integer to each one. The integer must be as short/small as possible . Is it possible to do that in Redis? Basically I need something like SADD but instead to return the number of elements in the set I need it to return the index of the element inserted(newly stored or existing).
Pseudo code:
// if mystring already exists in myset it returns its index
// otherwise stores it and returns its index.
index := storeOrReturnIndex(myset, mystring)
Would using a hashmap cover what you are looking for?
> HSET hashmap 0 "first string"
(integer) 1
> HSET hashmap 1 "second string"
(integer) 1
> HSET hashmap 2 "third string"
(integer) 1
> HGET hashmap 1
"second string"
> HLEN hashmap
3
You can store the last modified index in a key with:
> SET last_modified 1
Then retrieve it with:
> GET last_modified
You can use the Redis INCR command to atomically acquire a new, unique index.
Pattern: Counter
The counter pattern is the most obvious thing you can do with Redis atomic increment operations. The idea is simply send an INCR command to Redis every time an operation occurs. For instance in a web application we may want to know how many page views this user did every day of the year.
To do so the web application may simply increment a key every time the user performs a page view, creating the key name concatenating the User ID and a string representing the current date.
This simple pattern can be extended in many ways:
So use INCR to get the next unique, smallest index in an atomic way wherever you want to store a new item (URL). Then you can use HSET to store the index associated with your item, and HGET to get the associated index for an item.

How do I get a randomly selected hash key in Perl 6?

A quick and hopefully easy question:
I need the means to select from among a given set of hash keys at random. The perl6.org documentation on neither rand nor Hash offer many hints.
my %a = 1,2,3,4,5,6;
Given the above,
%a.keys;
returns (5 1 3) and if I simply try
%a.rand;
I get a pseudorandom float rather than any one key.
I eventually cobbled together %a.keys[Int(%a.elems.rand)], but was hoping for something simpler.
Use pick or roll, eg
%a.keys.pick
As always, Christoph's answer is correct (he knows PerlĀ 6 well). However, I thought I'd elaborate a little since pick and roll can easily be confused at first.
If you only want one random item, then pick and roll seem identical and can be used interchangeably because they both default to returning one item from the original list or array:
my $rand-keyA = %a.keys.pick;
my $rand-keyB = %a.keys.roll;
However, think of them this way:
pick means "Since there are only N things in this container, I can only pick up to N things at once."
roll means "I have an N-sided dice that I can roll as many times as I want."
my %a = 1,2,3,4,5,6; # { 1 => 2, 3 => 4, 5 => 6 }
# (i.e. keys are 1, 3, and 5)
say %a.keys.pick(2); # (5 3)
say %a.keys.pick(2); # (3 1)
say %a.keys.pick(5); # (3 5 1) no more, because there were only three to pick from
say %a.keys.pick(10); # (3 1 5)
say %a.keys.roll(5); # (1 5 1 5 3) as many "rolls" as you request
say %a.keys.roll(10); # (5 5 1 1 5 5 3 1 3 1)
pick(*) is an easy way to create a randomly reordered list from an array without having to know how many elements it has:
my #array = <foo bar baz foobar>;
#array.pick(*); # (bar foobar baz foo)
roll(*) is an easy way to create an infinite list whose elements are chosen randomly from the original array:
my #rolls = #array.roll(*);
say #rolls[0]; # foobar
say #rolls[10]; # bar
say #rolls[351]; # baz
say #rolls[19123]; # foobar
say #rolls[1000000]; # bar
say #rolls[1000001]; # bar
say #rolls[1000002]; # foo

Rails Redis Reset Counters to 0

I would like to reset the value of a REDIS counter to 0 in a Rails 4 app.
I use hincrby to increment counters
$redis.hincrby("user:likes", "key", 1)
I can't delete the key with hdel http://redis.io/commands/hdel because I need to get the key often.
GETSET is atomic and could do the job http://redis.io/commands/getset, as in the example
GETSET mycounter "0"
But since I use hashes I need to use HSET http://redis.io/commands/hset
$redis.hset("user:likes", "key", "0")
It's not specified if hset is atomic, anyone used hset to reset redis counters to 0? If it's not a good option to reset a counter to 0, any idea how to do it?
It is atomic, so if you run $redis.hset("user:likes", "key", "0"), it doesn't affect other fields inside the "user:likes" hash besides the field: "key"

How to sort a redis hash by values in keys

is there a good way in redis to get keys in a hash sorted by values? I've looked at the documentation and haven't found a straightforward way.
Also could someone please explain how sorting is achieved in redis, and what this documentation is trying to say?
I have a very simple hash structure which is something like this:
"salaries" - "employee_1" - "salary_amount"
I'd appreciate a detailed explanation.
You can achieve it by sorting a SET by one of your HASH fields. So you should create an indices SET of all of your hashes, and use the BY option.
Also, you can use DESC option to get the results sorted from high to low.
e.g.
localhost:6379> sadd indices h1 h2 h3 h4
(integer) 4
localhost:6379> hset h1 score 3
(integer) 1
localhost:6379> hset h2 score 2
(integer) 1
localhost:6379> hset h3 score 5
(integer) 1
localhost:6379> hset h4 score 1
(integer) 1
localhost:6379> sort indices by *->score
1) "h4"
2) "h2"
3) "h1"
4) "h3"
localhost:6379> sort indices by *->score desc
1) "h3"
2) "h1"
3) "h2"
4) "h4"
From SORT's documentation page:
Returns or stores the elements contained in the list, set or sorted set at key
So you can't really use it to sort the fields by their values in a Hash data structure. To achieve your goal you should either do the sorting in your application's code after getting the Hash's contents or use a Redis-embedded Lua script for that purpose.
Edit: After speaking with #OfirLuzon we realized that there is another, perhaps even preferable, approach which would be to use a more suitable data structure for this purpose. Instead of storing the salaries in a Hash, you should consider using a Sorted Set in which each member is an employee ID and the score is the relevant salary. This will give you ordering, ranges and paging for "free" :)

Resources