Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

No longer drives the solution #170

Merged
merged 3 commits into from
Jun 18, 2015
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 33 additions & 21 deletions largest-series-product/example.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,34 +3,46 @@
class Series
attr_reader :digits
def initialize(numeric_string)
@digits = convert_to_digits(numeric_string)
@digits = numeric_string
end

def largest_product(length)
fail ArgumentError.new('Not enough digits') if length > digits.length
products = []
slices(length).each do |slice|
products << slice.inject(1) do |product, n|
product * n
end
end
products.sort.last
@length = length
validate_length
analyzer
end

def slices(length)
result = []
i = -1
begin
i += 1
i2 = i + length - 1
result << digits[i..i2]
end while i2 < digits.size - 1
result
private

def validate_length
@length > digits.length and
fail(ArgumentError.new 'Not enough digits')
end

private
def analyzer
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

little naming nitpick: i think it's clearer when a method which returns something is named after the thing it returns, so maybe 'maximum' or if you want to show that the analysis is the important thing here I would say something like analysis_result. When you have a method called analyzer I would expect it to return a lambda (or object responding to call)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, naming is hard. But analyzer_result is a duplication, as result is assumed, probably, as it is the return of the method.

Maybe largest_value or even _largest_product to avoid the duplication of the method name itself?

collection_of_digits
select_max { reduce_to_product { validate { separate } } }
end

def validate
yield.take_while { |array| array.size == @length }
end

def reduce_to_product
yield.map { |array| array.inject(1, :*) }
end

def select_max
yield.max
end

def separate
digits.map.with_index do |_, index|
digits[index, @length]
end
end

def convert_to_digits(s)
s.chars.to_a.map(&:to_i)
def collection_of_digits
@digits = digits.chars.map(&:to_i)
end
end
71 changes: 6 additions & 65 deletions largest-series-product/largest_series_product_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -7,66 +7,7 @@
# rubocop:disable Lint/ParenthesesAsGroupedExpression
#
class Seriestest < Minitest::Test
def test_digits
assert_equal (0..9).to_a, Series.new('0123456789').digits
end

def test_same_digits_reversed
skip
assert_equal (0..9).to_a.reverse, Series.new('9876543210').digits
end

def test_fewer_digits
skip
assert_equal (4..8).to_a.reverse, Series.new('87654').digits
end

def test_some_other_digits
skip
assert_equal [9, 3, 6, 9, 2, 3, 4, 6, 8], Series.new('936923468').digits
end

def test_slices_of_zero
skip
assert_equal [], Series.new('').digits
end

def test_slices_of_2
skip
series = Series.new('01234')
expected = [[0, 1], [1, 2], [2, 3], [3, 4]]
assert_equal expected, series.slices(2)
end

def test_other_slices_of_2
skip
series = Series.new('98273463')
expected = [[9, 8], [8, 2], [2, 7], [7, 3], [3, 4], [4, 6], [6, 3]]
assert_equal expected, series.slices(2)
end

def test_slices_of_3
skip
series = Series.new('01234')
expected = [[0, 1, 2], [1, 2, 3], [2, 3, 4]]
assert_equal expected, series.slices(3)
end

def test_other_slices_of_3
skip
series = Series.new('982347')
expected = [[9, 8, 2], [8, 2, 3], [2, 3, 4], [3, 4, 7]]
assert_equal expected, series.slices(3)
end

def test_largest_product_of_2
skip
series = Series.new('0123456789')
assert_equal 72, series.largest_product(2)
end

def test_largest_product_of_a_tiny_number
skip
series = Series.new('12')
assert_equal 2, series.largest_product(2)
end
Expand All @@ -77,6 +18,12 @@ def test_another_tiny_number
assert_equal 9, series.largest_product(2)
end

def test_largest_product_of_2
skip
series = Series.new('0123456789')
assert_equal 72, series.largest_product(2)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i think it might be better to write 9*8 here to provide a little hint

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

and maybe for the 270 as well

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Message are better, as mentioned... add the largest series as a hint?

end

def test_largest_product_of_2_shuffled
skip
series = Series.new('576802143')
Expand Down Expand Up @@ -115,12 +62,6 @@ def test_some_other_big_number
assert_equal 28_350, series.largest_product(6)
end

def test_identity
skip
series = Series.new('')
assert_equal 1, series.largest_product(0)
end

def test_slices_bigger_than_number
skip
series = Series.new('123')
Expand Down