Skip to content

Instantly share code, notes, and snippets.

@tessi
Last active September 27, 2019 06:08
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save tessi/228bcd6fa68864515bed82e2434b5bdd to your computer and use it in GitHub Desktop.
Save tessi/228bcd6fa68864515bed82e2434b5bdd to your computer and use it in GitHub Desktop.
class ByteArray
include Enumerable
def initialize(n)
@size = n
@char_count = (n / 8.0).ceil
@store = String.new("\0" * @char_count, encoding: "ASCII-8BIT")
end
def [](n)
return nil if n >= @size
return nil if n < (@size * -1)
return self[@size + n] if n < 0
char_nr, bit_nr = n.divmod(8)
access(char_nr, bit_nr)
end
def []=(n, value)
return nil if n >= @size
return nil if n < (@size * -1)
return self[@size + n] = value if n < 0
char_nr, reverse_bit_nr = n.divmod(8)
bit_nr = 7 - reverse_bit_nr
new_int = @store[char_nr].getbyte(0)
if value
new_int = new_int | (1 << bit_nr)
else
new_int = new_int & (~0 ^ (1 << bit_nr))
end
@store[char_nr] = [new_int].pack('c')
end
def each
unless block_given?
return to_enum(__method__) { @size }
end
(0...@char_count).each do |char_nr|
(0...8).each do |bit_nr|
return if (char_nr + 1) * (bit_nr + 1) > @size
yield access(char_nr, bit_nr)
end
end
nil
end
private
def access(char_nr, reverse_bit_nr)
bit_nr = 7 - reverse_bit_nr
1 == (@store[char_nr].getbyte(0)[bit_nr])
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment