Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Merge pull request #744 from kostya/fill
Array#fill adapted from rubinius
  • Loading branch information
alex committed Jun 3, 2013
2 parents ee871cc + 47d4462 commit f16df06
Show file tree
Hide file tree
Showing 2 changed files with 61 additions and 39 deletions.
61 changes: 61 additions & 0 deletions lib-topaz/array.rb
Expand Up @@ -434,6 +434,67 @@ def repeated_permutation(r, &block)
self
end

def fill(*args, &block)
raise RuntimeError.new("can't modify frozen #{self.class}") if frozen?

if block
raise ArgumentError.new("wrong number of arguments (#{args.size} for 0..2)") if args.size > 2
one, two = args
else
raise ArgumentError.new("wrong number of arguments (#{args.size} for 1..3)") if args.empty? || args.size > 3
obj, one, two = args
end

if one.kind_of?(Range)
raise TypeError.new("no implicit conversion of Range into Integer") if two

left = Topaz.convert_type(one.begin, Fixnum, :to_int)
left += size if left < 0
raise RangeError.new("#{one} out of range") if left < 0

right = Topaz.convert_type(one.end, Fixnum, :to_int)
right += size if right < 0
right += 1 unless one.exclude_end?
return self if right <= left

elsif one
left = Topaz.convert_type(one, Fixnum, :to_int)
left += size if left < 0
left = 0 if left < 0

if two
right = Topaz.convert_type(two, Fixnum, :to_int)
return self if right == 0
right += left
else
right = size
end
else
left = 0
right = size
end

right_bound = (right > size) ? size : right

i = left
while i < right_bound
self[i] = block ? yield(i) : obj
i += 1
end

if left > size
self.concat([nil] * (left - size))
i = size
end

while i < right
self << (block ? yield(i) : obj)
i += 1
end

self
end

def transpose
return [] if self.empty?

Expand Down
39 changes: 0 additions & 39 deletions spec/tags/core/array/fill_tags.txt
@@ -1,40 +1 @@
fails:Array#fill returns self
fails:Array#fill is destructive
fails:Array#fill does not replicate the filler
fails:Array#fill replaces all elements in the array with the filler if not given a index nor a length
fails:Array#fill replaces all elements with the value of block (index given to block)
fails:Array#fill raises a RuntimeError on a frozen array
fails:Array#fill raises a RuntimeError on an empty frozen array
fails:Array#fill raises an ArgumentError if 4 or more arguments are passed when no block given
fails:Array#fill raises an ArgumentError if no argument passed and no block given
fails:Array#fill raises an ArgumentError if 3 or more arguments are passed when a block given
fails:Array#fill with (filler, index, length) replaces length elements beginning with the index with the filler if given an index and a length
fails:Array#fill with (filler, index, length) replaces length elements beginning with the index with the value of block
fails:Array#fill with (filler, index, length) replaces all elements after the index if given an index and no length
fails:Array#fill with (filler, index, length) replaces all elements after the index if given an index and nil as a length
fails:Array#fill with (filler, index, length) replaces the last (-n) elements if given an index n which is negative and no length
fails:Array#fill with (filler, index, length) replaces the last (-n) elements if given an index n which is negative and nil as a length
fails:Array#fill with (filler, index, length) makes no modifications if given an index greater than end and no length
fails:Array#fill with (filler, index, length) makes no modifications if given an index greater than end and nil as a length
fails:Array#fill with (filler, index, length) replaces length elements beginning with start index if given an index >= 0 and a length >= 0
fails:Array#fill with (filler, index, length) increases the Array size when necessary
fails:Array#fill with (filler, index, length) pads between the last element and the index with nil if given an index which is greater than size of the array
fails:Array#fill with (filler, index, length) replaces length elements beginning with the (-n)th if given an index n < 0 and a length > 0
fails:Array#fill with (filler, index, length) starts at 0 if the negative index is before the start of the array
fails:Array#fill with (filler, index, length) makes no modifications if the given length <= 0
fails:Array#fill with (filler, index, length) tries to convert the second and third arguments to Integers using #to_int
fails:Array#fill with (filler, index, length) raises a TypeError if the index is not numeric
fails:Array#fill with (filler, index, length) raises an ArgumentError or RangeError for too-large sizes
fails:Array#fill with (filler, range) replaces elements in range with object
fails:Array#fill with (filler, range) replaces all elements in range with the value of block
fails:Array#fill with (filler, range) increases the Array size when necessary
fails:Array#fill with (filler, range) raises a TypeError with range and length argument
fails:Array#fill with (filler, range) replaces elements between the (-m)th to the last and the (n+1)th from the first if given an range m..n where m < 0 and n >= 0
fails:Array#fill with (filler, range) replaces elements between the (-m)th and (-n)th to the last if given an range m..n where m < 0 and n < 0
fails:Array#fill with (filler, range) replaces elements between the (m+1)th from the first and (-n)th to the last if given an range m..n where m >= 0 and n < 0
fails:Array#fill with (filler, range) makes no modifications if given an range which implies a section of zero width
fails:Array#fill with (filler, range) makes no modifications if given an range which implies a section of negative width
fails:Array#fill with (filler, range) raise an exception if some of the given range lies before the first of the array
fails:Array#fill with (filler, range) tries to convert the start and end of the passed range to Integers using #to_int
fails:Array#fill with (filler, range) raises a TypeError if the start or end of the passed range is not numeric
fails:Array#fill with (filler, index, length)

0 comments on commit f16df06

Please sign in to comment.