class AVLTree::SortedSet(T)

Overview

SortedSet implements a Set that guarantees that its elements are yielded in sorted order (according to the return values of their #<=> methods) when iterating over them.

SortedSet utilizes an internally implemented SortedMap using an AVL tree.

While it often has slower computational speed compared to a Set implemented using a hash-based approach, it offers potential optimizations for operations related to order. For example, retrieving the maximum and minimum values of the set can be performed in logarithmic time.

SortedSet does not allow duplicates and only stores unique values.

Example

require "avltree"

set = AVLTree::SortedSet.new [3, 1, 4]
set.to_a == [1, 3, 4] # => true
set.to_a == [3, 1, 4] # => false

set << 1 << 5
set                 # => SortedSet{1, 3, 4, 5}
set.min             # => 1  (O(logN))
set.max             # => 5  (O(logN))
set.index(4)        # => 2  (O(logN))
set.upper_bound(2)  # => 1  (O(logN))
set.upper_bound(3)  # => 1  (O(logN))
set.upper_bound(10) # => 4  (O(logN))

Included Modules

Defined in:

avltree/sorted_set.cr

Constructors

Instance Method Summary

Instance methods inherited from module Enumerable(T)

to_sorted_multiset to_sorted_multiset, to_sorted_set to_sorted_set

Instance methods inherited from module Enumerable(T)

to_sorted_multiset to_sorted_multiset, to_sorted_set to_sorted_set

Constructor Detail

def self.new(other : Indexable(T)) #

[View source]
def self.new(enumerable : Enumerable(T)) #

[View source]
def self.new #

[View source]

Instance Method Detail

def &(other : SortedSet) : SortedSet(T) #

[View source]
def +(other : SortedSet(U)) : SortedSet(T | U) forall U #

[View source]
def -(other : SortedSet) #

[View source]
def -(other : Enumerable) #

[View source]
def <<(object : T) #

[View source]
def ==(other : SortedSet) #

[View source]
def ===(other : T) #

[View source]
def ^(other : SortedSet(U)) forall U #

[View source]
def ^(other : Enumerable(U)) forall U #

[View source]
def |(other : SortedSet(U)) : SortedSet(U | T) forall U #

[View source]
def add(object : T) #

[View source]
def add?(object : T) #

[View source]
def at(index : Int) #

Returns the element at the index-th.


[View source]
def at(index : Int, &) #

Returns the element at the index-th.


[View source]
def at?(index : Int) #

Like #at, but returns nil if trying to access an element outside the set's range.


[View source]
def clear #

Removes all elements in the set, and returns self.


[View source]
def clone #

[View source]
def concat(elems) #

[View source]
def count(range : Range(T | Nil, T | Nil)) #

Returns the number of elements in the set that exist within the range.

set = AVLTree::SortedSet(Int32){3, 1, 4, 1, 5, 9}
set.count(2..3)  # => 1
set.count(2...3) # => 0
set.count(2..9)  # => 4
set.count(2...9) # => 3
set.count(2...)  # => 4
set.count(...)   # => 5
set.count(...9)  # => 4

[View source]
def count(object) #
Description copied from module Enumerable(T)

Returns the number of times that the passed item is present in the collection.

[1, 2, 3, 4].count(3) # => 1

[View source]
def delete(object) #

Removes the object from the set and returns true if it was present, otherwise returns false.


[View source]
def delete_at(index : Int, &) #

Removes the index-th object and returns the deleted object, else yields #index with given block.


[View source]
def delete_at(index : Int) : T #

Removes the index-th object from the set and returns the deleted object.


[View source]
def delete_at?(index : Int) : T | Nil #

Removes the index-th object from the set and returns the deleted object if it was present, otherwise returns nil.


[View source]
def dup #
Description copied from class Reference

Returns a shallow copy of this object.

This allocates a new object and copies the contents of self into it.


[View source]
def each(&) #
Description copied from module Indexable(T)

Calls the given block once for each element in self, passing that element as a parameter.

a = ["a", "b", "c"]
a.each { |x| print x, " -- " }

produces:

a -- b -- c --

[View source]
def each #
Description copied from module Iterable(T)

Must return an Iterator over the elements in this collection.


[View source]
def empty? #
Description copied from module Indexable(T)

Returns true if self is empty, false otherwise.

([] of Int32).empty? # => true
([1]).empty?         # => false

[View source]
def fetch(index : Int, &) #
Description copied from module Indexable(T)

Returns the element at the given index, if in bounds, otherwise executes the given block with the index and returns its value.

a = [:foo, :bar]
a.fetch(0) { :default_value }    # => :foo
a.fetch(2) { :default_value }    # => :default_value
a.fetch(2) { |index| index * 3 } # => 6

[View source]
def fetch(index : Int, default) #

[View source]
def first #
Description copied from module Enumerable(T)

Returns the first element in the collection. Raises Enumerable::EmptyError if the collection is empty.

([1, 2, 3]).first   # => 1
([] of Int32).first # raises Enumerable::EmptyError

[View source]
def first? #
Description copied from module Enumerable(T)

Returns the first element in the collection. When the collection is empty, returns nil.

([1, 2, 3]).first?   # => 1
([] of Int32).first? # => nil

[View source]
def hash(hasher) #
Description copied from module Indexable(T)

See Object#hash(hasher)


[View source]
def includes?(object) #
Description copied from module Enumerable(T)

Returns true if the collection contains obj, false otherwise.

[1, 2, 3].includes?(2) # => true
[1, 2, 3].includes?(5) # => false

[View source]
def index(object) #
Description copied from module Indexable(T)

Returns the index of the first appearance of object in self starting from the given offset, or nil if object is not in self.

[1, 2, 3, 1, 2, 3].index(2, offset: 2) # => 4

[View source]
def index!(object) #
Description copied from module Indexable(T)

Returns the index of the first appearance of obj in self starting from the given offset. Raises Enumerable::NotFoundError if obj is not in self.

[1, 2, 3, 1, 2, 3].index!(2, offset: 2) # => 4

[View source]
def index_of_largest_leq(object) : Int32 | Nil #

See SortedMap#largest_leq_index


[View source]
def index_of_largest_lt(object) : Int32 | Nil #

See SortedMap#largest_lt_index


[View source]
def index_of_smallest_geq(object) : Int32 | Nil #

See SortedMap#smallest_geq_index


[View source]
def index_of_smallest_gt(object) : Int32 | Nil #

See SortedMap#smallest_gt_index


[View source]
def inspect(io : IO) : Nil #
Description copied from class Reference

Appends a String representation of this object which includes its class name, its object address and the values of all instance variables.

class Person
  def initialize(@name : String, @age : Int32)
  end
end

Person.new("John", 32).inspect # => #<Person:0x10fd31f20 @name="John", @age=32>

[View source]
def intersects?(other : Set) #

[View source]
def largest_leq(object) : T | Nil #

[View source]
def largest_leq_with_index(object) : Tuple(T | Nil, Int32 | Nil) #

[View source]
def largest_lt(object) : T | Nil #

[View source]
def largest_lt_with_index(object) : Tuple(T | Nil, Int32 | Nil) #

[View source]
def last #
Description copied from module Indexable(T)

Returns the last element of self if it's not empty, or raises IndexError.

([1, 2, 3]).last   # => 3
([] of Int32).last # raises IndexError

[View source]
def last? #
Description copied from module Indexable(T)

Returns the last element of self if it's not empty, or nil.

([1, 2, 3]).last?   # => 3
([] of Int32).last? # => nil

[View source]
def lower_bound(object) : Int32 #
set = AVLTree::SortedSet(String){"A", "B", "B", "C", "E"}
set                  # => SortedSet{"A", "B", "C", "E"}
set.lower_bound("@") # => 0
set.lower_bound("A") # => 0
set.lower_bound("B") # => 1
set.lower_bound("C") # => 2
set.lower_bound("D") # => 3
set.lower_bound("E") # => 3
set.lower_bound("F") # => 4
set.lower_bound("Z") # => 4

[View source]
def max #
Description copied from module Enumerable(T)

Returns the element with the maximum value in the collection.

It compares using > so it will work for any type that supports that method.

[1, 2, 3].max        # => 3
["Alice", "Bob"].max # => "Bob"

Raises Enumerable::EmptyError if the collection is empty.


[View source]
def max? #
Description copied from module Enumerable(T)

Like #max but returns nil if the collection is empty.


[View source]
def min #
Description copied from module Enumerable(T)

Returns the element with the minimum value in the collection.

It compares using < so it will work for any type that supports that method.

[1, 2, 3].min        # => 1
["Alice", "Bob"].min # => "Alice"

Raises Enumerable::EmptyError if the collection is empty.


[View source]
def min? #
Description copied from module Enumerable(T)

Like #min but returns nil if the collection is empty.


[View source]
def object_id #
Description copied from class Reference

Returns a UInt64 that uniquely identifies this object.

The returned value is the memory address of this object.

string = "hello"
string.object_id # => 4460249568

pointer = Pointer(String).new(string.object_id)
string2 = pointer.as(String)
string2.object_id == string.object_id # => true

[View source]
def pop : T #

[View source]
def pop(&) #

[View source]
def pop? : T | Nil #

[View source]
def pretty_print(pp) : Nil #

[View source]
def proper_subset_of?(other : SortedSet) #

[View source]
def proper_superset_of?(other : SortedSet) #

[View source]
def rindex(object) #
Description copied from module Indexable(T)

Returns the index of the last appearance of value in self, or nil if the value is not in self.

If offset is given, it defines the position to end the search (elements beyond this point are ignored).

[1, 2, 3, 2, 3].rindex(2)            # => 3
[1, 2, 3, 2, 3].rindex(2, offset: 2) # => 1

[View source]
def rindex!(object) #
Description copied from module Indexable(T)

Returns the index of the last appearance of value in self, or nil if the value is not in self.

If offset is given, it defines the position to end the search (elements beyond this point are ignored).

[1, 2, 3, 2, 3].rindex(2)            # => 3
[1, 2, 3, 2, 3].rindex(2, offset: 2) # => 1

Raises Enumerable::NotFoundError if value is not in self.


[View source]
def same?(other : SortedSet) #
Description copied from class Reference

Returns true if this reference is the same as other. This is only true if this reference's #object_id is the same as other's.


[View source]
def shift : T #

[View source]
def shift(&) #

[View source]
def shift? : T | Nil #

[View source]
def size #
Description copied from module Indexable(T)

Returns the number of elements in this container.


[View source]
def smallest_geq(object) : T | Nil #

[View source]
def smallest_geq_with_index(object) : Tuple(T | Nil, Int32 | Nil) #

[View source]
def smallest_gt(object) : T | Nil #

[View source]
def smallest_gt_with_index(object) : Tuple(T | Nil, Int32 | Nil) #

[View source]
def subset_of?(other : SortedSet) #

[View source]
def subtract(other : Enumerable) #

[View source]
def superset_of?(other : SortedSet) #

[View source]
def to_a #
Description copied from module Indexable(T)

Returns an Array with all the elements in the collection.

{1, 2, 3}.to_a # => [1, 2, 3]

[View source]
def to_s(io : IO) : Nil #
Description copied from class Reference

Appends a short String representation of this object which includes its class name and its object address.

class Person
  def initialize(@name : String, @age : Int32)
  end
end

Person.new("John", 32).to_s # => #<Person:0x10a199f20>

[View source]
def unordered_each(&) #

Yields each element of the set, and returns self.

It doesn't guarantee that its elements are yielded in sorted order when iterating over them.


[View source]
def unsafe_fetch(index : Int) #
Description copied from module Indexable(T)

Returns the element at the given index, without doing any bounds check.

Indexable makes sure to invoke this method with index in 0...size, so converting negative indices to positive ones is not needed here.

Clients never invoke this method directly. Instead, they access elements with #[](index) and #[]?(index).

This method should only be directly invoked if you are absolutely sure the index is in bounds, to avoid a bounds check for a small boost of performance.


[View source]
def upper_bound(object) : Int32 #
set = AVLTree::SortedSet(String){"A", "B", "B", "C", "E"}
set                  # => SortedSet{"A", "B", "C", "E"}
set.upper_bound("@") # => 0
set.upper_bound("A") # => 1
set.upper_bound("B") # => 2
set.upper_bound("C") # => 3
set.upper_bound("D") # => 3
set.upper_bound("E") # => 4
set.upper_bound("F") # => 4
set.upper_bound("Z") # => 4

[View source]