summaryrefslogtreecommitdiffhomepage
path: root/mrbgems/mruby-array-ext/mrblib
diff options
context:
space:
mode:
Diffstat (limited to 'mrbgems/mruby-array-ext/mrblib')
-rw-r--r--mrbgems/mruby-array-ext/mrblib/array.rb267
1 files changed, 95 insertions, 172 deletions
diff --git a/mrbgems/mruby-array-ext/mrblib/array.rb b/mrbgems/mruby-array-ext/mrblib/array.rb
index ed3f591fe..7520b932f 100644
--- a/mrbgems/mruby-array-ext/mrblib/array.rb
+++ b/mrbgems/mruby-array-ext/mrblib/array.rb
@@ -1,32 +1,6 @@
-# coding: cp932
class Array
##
# call-seq:
- # Array.try_convert(obj) -> array or nil
- #
- # Tries to convert +obj+ into an array, using +to_ary+ method.
- # converted array or +nil+ if +obj+ cannot be converted for any reason.
- # This method can be used to check if an argument is an array.
- #
- # Array.try_convert([1]) #=> [1]
- # Array.try_convert("1") #=> nil
- #
- # if tmp = Array.try_convert(arg)
- # # the argument is an array
- # elsif tmp = String.try_convert(arg)
- # # the argument is a string
- # end
- #
- def self.try_convert(obj)
- if obj.respond_to?(:to_ary)
- obj.to_ary
- else
- nil
- end
- end
-
- ##
- # call-seq:
# ary.uniq! -> ary or nil
# ary.uniq! { |item| ... } -> ary or nil
#
@@ -77,7 +51,7 @@ class Array
# b.uniq { |s| s.first } # => [["student", "sam"], ["teacher", "matz"]]
#
def uniq(&block)
- ary = self.dup
+ ary = self[0..-1]
ary.uniq!(&block)
ary
end
@@ -116,6 +90,22 @@ class Array
##
# call-seq:
+ # ary.difference(other_ary1, other_ary2, ...) -> new_ary
+ #
+ # Returns a new array that is a copy of the original array, removing all
+ # occurrences of any item that also appear in +other_ary+. The order is
+ # preserved from the original array.
+ #
+ def difference(*args)
+ ary = self
+ args.each do |x|
+ ary = ary - x
+ end
+ ary
+ end
+
+ ##
+ # call-seq:
# ary | other_ary -> new_ary
#
# Set Union---Returns a new array by joining this array with
@@ -160,7 +150,7 @@ class Array
# [ 1, 1, 3, 5 ] & [ 1, 2, 3 ] #=> [ 1, 3 ]
#
def &(elem)
- raise TypeError, "can't convert #{elem.class} into Array" unless elem.class == Array
+ raise TypeError, "cannot convert #{elem.class} into Array" unless elem.class == Array
hash = {}
array = []
@@ -185,6 +175,65 @@ class Array
##
# call-seq:
+ # ary.intersection(other_ary,...) -> new_ary
+ #
+ # Set Intersection---Returns a new array containing elements common to
+ # this array and <i>other_ary</i>s, removing duplicates. The order is
+ # preserved from the original array.
+ #
+ # [1, 2, 3].intersection([3, 4, 1], [1, 3, 5]) #=> [1, 3]
+ #
+ def intersection(*args)
+ ary = self
+ args.each do |x|
+ ary = ary & x
+ end
+ ary
+ end
+
+ ##
+ # call-seq:
+ # ary.intersect?(other_ary) -> true or false
+ #
+ # Returns +true+ if the array and +other_ary+ have at least one element in
+ # common, otherwise returns +false+.
+ #
+ # a = [ 1, 2, 3 ]
+ # b = [ 3, 4, 5 ]
+ # c = [ 5, 6, 7 ]
+ # a.intersect?(b) #=> true
+ # a.intersect?(c) #=> false
+ def intersect?(ary)
+ raise TypeError, "cannot convert #{ary.class} into Array" unless ary.class == Array
+
+ hash = {}
+ if self.length > ary.length
+ shorter = ary
+ longer = self
+ else
+ shorter = self
+ longer = ary
+ end
+ idx = 0
+ len = shorter.size
+ while idx < len
+ hash[shorter[idx]] = true
+ idx += 1
+ end
+ idx = 0
+ len = size
+ while idx < len
+ v = longer[idx]
+ if hash[v]
+ return true
+ end
+ idx += 1
+ end
+ false
+ end
+
+ ##
+ # call-seq:
# ary.flatten -> new_ary
# ary.flatten(level) -> new_ary
#
@@ -201,7 +250,7 @@ class Array
# a.flatten(1) #=> [1, 2, 3, [4, 5]]
#
def flatten(depth=nil)
- res = dup
+ res = Array.new(self)
res.flatten! depth
res
end
@@ -245,41 +294,6 @@ class Array
end
end
- ##
- # call-seq:
- # ary.compact -> new_ary
- #
- # Returns a copy of +self+ with all +nil+ elements removed.
- #
- # [ "a", nil, "b", nil, "c", nil ].compact
- # #=> [ "a", "b", "c" ]
- #
- def compact
- result = self.dup
- result.compact!
- result
- end
-
- ##
- # call-seq:
- # ary.compact! -> ary or nil
- #
- # Removes +nil+ elements from the array.
- # Returns +nil+ if no changes were made, otherwise returns
- # <i>ary</i>.
- #
- # [ "a", nil, "b", nil, "c" ].compact! #=> [ "a", "b", "c" ]
- # [ "a", "b", "c" ].compact! #=> nil
- #
- def compact!
- result = self.select { |e| !e.nil? }
- if result.size == self.size
- nil
- else
- self.replace(result)
- end
- end
-
# for efficiency
def reverse_each(&block)
return to_enum :reverse_each unless block
@@ -292,7 +306,6 @@ class Array
self
end
- NONE=Object.new
##
# call-seq:
# ary.fetch(index) -> obj
@@ -317,8 +330,8 @@ class Array
# #=> "100 is out of bounds"
#
- def fetch(n=nil, ifnone=NONE, &block)
- warn "block supersedes default value argument" if !n.nil? && ifnone != NONE && block
+ def fetch(n, ifnone=NONE, &block)
+ #warn "block supersedes default value argument" if !n.nil? && ifnone != NONE && block
idx = n
if idx < 0
@@ -373,7 +386,6 @@ class Array
end
beg = len = 0
- ary = []
if block
if arg0.nil? && arg1.nil? && arg2.nil?
# ary.fill { |index| block } -> ary
@@ -437,57 +449,6 @@ class Array
##
# call-seq:
- # ary.rotate(count=1) -> new_ary
- #
- # Returns a new array by rotating +self+ so that the element at +count+ is
- # the first element of the new array.
- #
- # If +count+ is negative then it rotates in the opposite direction, starting
- # from the end of +self+ where +-1+ is the last element.
- #
- # a = [ "a", "b", "c", "d" ]
- # a.rotate #=> ["b", "c", "d", "a"]
- # a #=> ["a", "b", "c", "d"]
- # a.rotate(2) #=> ["c", "d", "a", "b"]
- # a.rotate(-3) #=> ["b", "c", "d", "a"]
-
- def rotate(count=1)
- ary = []
- len = self.length
-
- if len > 0
- idx = (count < 0) ? (len - (~count % len) - 1) : (count % len) # rotate count
- len.times do
- ary << self[idx]
- idx += 1
- idx = 0 if idx > len-1
- end
- end
- ary
- end
-
- ##
- # call-seq:
- # ary.rotate!(count=1) -> ary
- #
- # Rotates +self+ in place so that the element at +count+ comes first, and
- # returns +self+.
- #
- # If +count+ is negative then it rotates in the opposite direction, starting
- # from the end of the array where +-1+ is the last element.
- #
- # a = [ "a", "b", "c", "d" ]
- # a.rotate! #=> ["b", "c", "d", "a"]
- # a #=> ["b", "c", "d", "a"]
- # a.rotate!(2) #=> ["d", "a", "b", "c"]
- # a.rotate!(-3) #=> ["a", "b", "c", "d"]
-
- def rotate!(count=1)
- self.replace(self.rotate(count))
- end
-
- ##
- # call-seq:
# ary.delete_if { |item| block } -> ary
# ary.delete_if -> Enumerator
#
@@ -681,37 +642,6 @@ class Array
##
# call-seq:
- # ary.delete_if { |item| block } -> ary
- # ary.delete_if -> Enumerator
- #
- # Deletes every element of +self+ for which block evaluates to +true+.
- #
- # The array is changed instantly every time the block is called, not after
- # the iteration is over.
- #
- # See also Array#reject!
- #
- # If no block is given, an Enumerator is returned instead.
- #
- # scores = [ 97, 42, 75 ]
- # scores.delete_if {|score| score < 80 } #=> [97]
-
- def delete_if(&block)
- return to_enum :delete_if unless block
-
- idx = 0
- while idx < self.size do
- if block.call(self[idx])
- self.delete_at(idx)
- else
- idx += 1
- end
- end
- self
- end
-
- ##
- # call-seq:
# ary.keep_if { |item| block } -> ary
# ary.keep_if -> Enumerator
#
@@ -729,7 +659,6 @@ class Array
return to_enum :keep_if unless block
idx = 0
- len = self.size
while idx < self.size do
if block.call(self[idx])
idx += 1
@@ -799,16 +728,6 @@ class Array
end
##
- # call-seq:
- # ary.to_ary -> ary
- #
- # Returns +self+.
- #
- def to_ary
- self
- end
-
- ##
# call-seq:
# ary.dig(idx, ...) -> object
#
@@ -852,12 +771,11 @@ class Array
# a.permutation(0).to_a #=> [[]] # one permutation of length 0
# a.permutation(4).to_a #=> [] # no permutations of length 4
def permutation(n=self.size, &block)
- size = self.size
return to_enum(:permutation, n) unless block
- return if n > size
+ size = self.size
if n == 0
- yield []
- else
+ yield []
+ elsif 0 < n && n <= size
i = 0
while i<size
result = [self[i]]
@@ -872,6 +790,7 @@ class Array
i += 1
end
end
+ self
end
##
@@ -898,9 +817,8 @@ class Array
# a.combination(5).to_a #=> [] # no combinations of length 5
def combination(n, &block)
- size = self.size
return to_enum(:combination, n) unless block
- return if n > size
+ size = self.size
if n == 0
yield []
elsif n == 1
@@ -909,7 +827,7 @@ class Array
yield [self[i]]
i += 1
end
- else
+ elsif n <= size
i = 0
while i<size
result = [self[i]]
@@ -919,6 +837,7 @@ class Array
i += 1
end
end
+ self
end
##
@@ -927,7 +846,7 @@ class Array
#
# Assumes that self is an array of arrays and transposes the rows and columns.
#
- # If the length of the subarrays don’t match, an IndexError is raised.
+ # If the length of the subarrays don't match, an IndexError is raised.
#
# Examples:
#
@@ -940,8 +859,8 @@ class Array
column_count = nil
self.each do |row|
raise TypeError unless row.is_a?(Array)
- column_count ||= row.count
- raise IndexError, 'element size differs' unless column_count == row.count
+ column_count ||= row.size
+ raise IndexError, 'element size differs' unless column_count == row.size
end
Array.new(column_count) do |column_index|
@@ -954,7 +873,7 @@ class Array
# ary.to_h -> Hash
# ary.to_h{|item| ... } -> Hash
#
- # Returns the result of interpreting <i>aray</i> as an array of
+ # Returns the result of interpreting <i>array</i> as an array of
# <tt>[key, value]</tt> pairs. If a block is given, it should
# return <tt>[key, value]</tt> pairs to construct a hash.
#
@@ -973,4 +892,8 @@ class Array
end
h
end
+
+ alias append push
+ alias prepend unshift
+ alias filter! select!
end