class Redstruct::SortedSet
Mapping between Redis and Ruby sorted sets (with scores). There is no caching mechanism in play, so most methods actually do access the underlying redis connection. Also, keep in mind Redis converts all values strings on the DB side
Public Class Methods
@param [Boolean] lex if true, assumes the set is lexicographically sorted
Redstruct::Struct::new
# File lib/redstruct/sorted_set.rb, line 14 def initialize(lex: false, **options) super(**options) @lex = lex end
Public Instance Methods
@param [Array<#to_s>] values the object to add to the set @param [Boolean] exists if true, only update elements that exist (do not add new ones) @param [Boolean] overwrite if false, do not update existing elements @return [Integer] the number of elements that have changed (includes new ones)
# File lib/redstruct/sorted_set.rb, line 28 def add(*values, exists: false, overwrite: true) options = { xx: exists, nx: !overwrite, ch: true } if @lex values = values.map do |pair| member = pair.is_a?(Array) ? pair.last : pair [0.0, member] end end return self.connection.zadd(@key, values, options) end
Removes all items from the set. Does this by simply deleting the key @see Redstruct::Struct#delete
# File lib/redstruct/sorted_set.rb, line 58 def clear delete end
Relies on the score method, since it is O(1), whereas the index method is O(logn) @param [#to_s] item the item to check for @return [Boolean] true if the item is in the set, false otherwise
# File lib/redstruct/sorted_set.rb, line 93 def contain?(item) return coerce_bool(score(item)) end
@param [#to_s] member the member of the set whose score to decrement @param [#to_f] by the amount to decrement the score by @return [Float] the new score of the member
# File lib/redstruct/sorted_set.rb, line 52 def decrement(member, by: 1.0) return increment(member, by: -by.to_f) end
Checks if the set contains any items. @return [Boolean] true if the key exists (meaning it contains at least 1 item), false otherwise
# File lib/redstruct/sorted_set.rb, line 85 def empty? return !exists? end
@param [#to_s] member the member of the set whose score to increment @param [#to_f] by the amount to increment the score by @return [Float] the new score of the member
# File lib/redstruct/sorted_set.rb, line 44 def increment(member, by: 1.0) raise NotImplementedError, 'cannot increment the score of items in a lexicographically ordered set' if @lex return self.connection.zincrby(@key, by.to_f, member.to_s).to_f end
Returns the index of the item in the set, sorted ascending by score @param [#to_s] item the item to check for @return [Integer, nil] the index of the item, or nil if not found
# File lib/redstruct/sorted_set.rb, line 101 def index(item) return self.connection.zrank(@key, item) end
@return [Boolean] true if this is a lexicographically sorted set
# File lib/redstruct/sorted_set.rb, line 20 def lexicographic? return @lex end
Removes the items from the set. @param [Array<#to_s>] items the items to remove from the set @return [Integer] the amount of items removed from the set
# File lib/redstruct/sorted_set.rb, line 122 def remove(*items) return self.connection.zrem(@key, items) end
Returns the index of the item in the set, sorted descending by score @param [#to_s] item the item to check for @return [Integer, nil] the index of the item, or nil if not found
# File lib/redstruct/sorted_set.rb, line 108 def rindex(item) return self.connection.zrevrank(@key, item) end
Returns the score of the given item. @param [#to_s] item the item to check for @return [Float, nil] the score of the item, or nil if not found
# File lib/redstruct/sorted_set.rb, line 115 def score(item) return self.connection.zscore(@key, item) end
Returns the number of items in the set. If you want to specify within a range, first get the slice and query its size. @return [Integer] the number of items in the set
# File lib/redstruct/sorted_set.rb, line 65 def size return self.connection.zcard(@key) end
Returns a slice or partial selection of the set. @see Redstruct::SortedSet::Slice#initialize @return [Redstruct::SortedSet::Slice] a newly created slice for this set
# File lib/redstruct/sorted_set.rb, line 72 def slice(**options) defaults = { lower: nil, upper: nil, exclusive: false, lex: @lex } self.class::Slice.new(self, **defaults.merge(options)) end
Returns an array representation of the set, sorted by score ascending NOTE: It pulls the whole set into memory, so use each if that's a concern, or use slices with pre-determined ranges. @return [Array<Redstruct::Utils::ScoredValue>] all the items in the set, sorted by score ascending
# File lib/redstruct/sorted_set.rb, line 130 def to_a return slice.to_a end
Use redis-rb zscan_each method to iterate over particular keys @return [Enumerator] base enumerator to iterate of the namespaced keys
# File lib/redstruct/sorted_set.rb, line 142 def to_enum(match: '*', count: 10, with_scores: false) enumerator = self.connection.zscan_each(@key, match: match, count: count) return enumerator if with_scores return Enumerator.new do |yielder| loop do item, = enumerator.next yielder << item end end end
TODO: Consider using ::SortedSet or some other data structure @return [::Set] an unordered set representation
# File lib/redstruct/sorted_set.rb, line 136 def to_set return slice.to_set end