Skip to content

Commit b7b9911

Browse files
committed
Add Array#subtract
1 parent 17138ae commit b7b9911

File tree

2 files changed

+66
-0
lines changed

2 files changed

+66
-0
lines changed

lib/core/facets/array/subtract.rb

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
class Array
2+
# Returns a new array that is a copy of the original array, removing the _first_ item in self that
3+
# also appears in other. The order is preserved from the original array.
4+
#
5+
# For each element of `other`, deletes the _first_ item from self that is equal to element (using
6+
# `delete_at`, not `delete`).
7+
#
8+
# This is similar to `Array#-` and `Array#difference`, except that instead of removing _all_
9+
# matches, it only removes as many occurrences as you actually _ask_ it to subtract:
10+
#
11+
# > [1, 1, 2].subtract [1]
12+
# => [1, 2]
13+
#
14+
# > [1, 1, 2].subtract [1, 1]
15+
# => [2]
16+
#
17+
# > [1, 1, 2] - [1]
18+
# => [2]
19+
#
20+
# > [1, 1, 2].difference [1]
21+
# => [2]
22+
#
23+
def subtract(other)
24+
dup.subtract!(other)
25+
end
26+
27+
# Removes the _first_ item in self that also appears in other.
28+
#
29+
# This is the in-place version of subtract.
30+
#
31+
def subtract!(other)
32+
other.each do |el|
33+
delete_at(index(el))
34+
end
35+
self
36+
end
37+
end

test/core/array/test_subtract.rb

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
covers 'facets/array/subtract'
2+
3+
test_case Array do
4+
method :subtract do
5+
test do
6+
a = [1,1,2,3]
7+
a.subtract( [1]).assert == [ 1,2,3]
8+
a.difference([1]).assert == [ 2,3]
9+
(a - [1]).assert == [ 2,3]
10+
a.assert == [1,1,2,3]
11+
end
12+
13+
test do
14+
a = [1,1,2,3]
15+
a.subtract([1, 1]).assert == [ 2,3]
16+
(a - [1]).assert == [ 2,3]
17+
a.assert == [1,1,2,3]
18+
end
19+
end
20+
21+
method :subtract! do
22+
test do
23+
a = [1,1,2,3]
24+
a.subtract!([1]).assert == [ 1,2,3]
25+
a.assert == [ 1,2,3]
26+
end
27+
end
28+
end
29+

0 commit comments

Comments
 (0)