Method that returns result and modulo - ruby

I am trying to write a method that asks for two 2 integers, and divides the first by the second and returns the result including the remainder.
def remainder(a,b)
return a/b
return a%b
end
puts remainder(100,6)
This puts out
16
If I use this code
def remainder(a,b)
return a%b
end
puts remainder(100,6)
This puts out
4
I don't understand how to make both the modulus value and the remainder show in puts statement.
Update
Based on Simple Lime's advice I used the following code...
def remainder(a,b)
return a.divmod(b)
end
puts remainder(100,6)
Which puts
16
4
And is functioning as I had hoped.

You can return an array from the method when you need to return multiple values:
def remainder(a, b)
[a / b, a % b]
end
puts remainder(100, 6).inspect # => [16, 4]
and then you can assign each value to a different variable, if you need:
div, mod = remainder(100, 6)
puts div # => 16
puts mod # => 4
As a side note, if you are just needing both the quotient and modulus of 2 numbers, there's already a built-in function, divmod that does this, using the technique above:
100.divmod(6) # => [16, 4]

Related

How to create a "clone"-able enumerator for external iteration?

I want to create an enumerator for external iteration via next that is clone-able, so that the clone retains the current enumeration state.
As an example, let's say I have a method that returns an enumerator which yields square numbers:
def square_numbers
return enum_for(__method__) unless block_given?
n = d = 1
loop do
yield n
d += 2
n += d
end
end
square_numbers.take(10)
#=> [1, 4, 9, 16, 25, 36, 49, 64, 81, 100]
And I want to enumerate the first 5 square numbers, and for each value, print the subsequent 3 square numbers. Something that's trivial with each_cons:
square_numbers.take(8).each_cons(4) do |a, *rest|
printf("%2d: %2d %2d %2d\n", a, *rest)
end
Output:
1: 4 9 16
4: 9 16 25
9: 16 25 36
16: 25 36 49
25: 36 49 64
But unlike the above, I want to use external iteration using two nested loops along with next and clone:
outer_enum = square_numbers
5.times do
i = outer_enum.next
printf('%2d:', i)
inner_enum = outer_enum.clone
3.times do
j = inner_enum.next
printf(' %2d', j)
end
print("\n")
end
Unfortunately, the above attempt to clone raises a:
`initialize_copy': can't copy execution context (TypeError)
I understand that Ruby doesn't provide this out-of-the-box. But how can I implement it myself? How can I create an Enumerator that supports clone?
I assume that it's a matter of implementing initialize_copy and copying the two variable values for n and d, but I don't know how or where to do it.
Ruby fibers cannot be copied, and the C implementation of Enumerator stores a pointer to a fiber which does not appear to be exposed to Ruby code in any way.
https://github.com/ruby/ruby/blob/752041ca11c7e08dd14b8efe063df06114a9660f/enumerator.c#L505
if (ptr0->fib) {
/* Fibers cannot be copied */
rb_raise(rb_eTypeError, "can't copy execution context");
}
Looking through the C source, it's apparent that Enumerators and Fibers are connected in a pretty profound way. So I doubt that there is any way to change the behavior of initialize_copy to permit clone.
Perhaps you could just write a class of your own that does what you ask:
class NumberSquarer
def initialize
#n = #d = 1
end
def next
ret = #n
#d += 2
#n += #d
ret
end
end
ns1 = NumberSquarer.new
Array.new(5) { ns1.next }
# => [1, 4, 9, 16, 25]
ns2 = ns1.clone
Array.new(5) { ns2.next }
# => [36, 49, 64, 81, 100]
Disclaimer: I'm answering my own question
One way to achieve this is by sub-classing Enumerator. In particular, the now-deprecated variant that takes an object and a method:
class ObjectEnumerator < Enumerator
attr_reader :object, :method
def initialize(object, method = :each)
#object = object
#method = method
super
end
def initialize_copy(orig)
initialize(orig.object.clone, orig.method)
end
end
That orig.object.clone above is where the magic happens: it clones the object we are traversing.
In addition, we need such clone-able object. A simple way is to have a class which holds the state as instance variables: (shamelessly copied from Kache's answer)
class NumberSquarer
def initialize
#d = -1
#n = 0
end
def each
return ObjectEnumerator.new(self, __method__) unless block_given?
loop do
#d += 2
#n += #d # had to be reordered b/c
yield #n # <- yield has to come last
end
end
end
This gives us a basic, clone-able enumerator:
e = NumberSquarer.new.each
#=> #<ObjectEnumerator: #<NumberSquarer:0x00007fde60915e10 #d=-1, #n=0>:each>
e.next #=> 1
e.next #=> 4
other = enum.clone
#=> #<ObjectEnumerator: #<NumberSquarer:0x00007fcf23842520 #d=3, #n=4>:each>
enum.next #=> 9
enum.next #=> 16
other.next #=> 9
I'm providing a different solution that is not a straight answer to the question:
How can I create an Enumerator that supports clone?
But if I'm not wrong the only purpose of cloning the not clonable Ruby's Enumerator is to get a reference to the next object in the enumerator.
In this case, we need both values stored in odd_sum and square in the example below.
We can store those values in an Array and return the array instead of a single value, then we can use Enumerator.peek in order to have the array that is used to initialize a new Enumerator.
def square_numbers(starters = {})
return enum_for(__method__, starters) unless block_given?
last_odd = starters.fetch(:square_odd, [1,1])[1]
square = starters.fetch(:square_odd, [1,1])[0]
loop do
yield [square, last_odd]
last_odd += 2
square += last_odd
end
end
outer_enum = square_numbers
5.times do
i = outer_enum.next[0]
printf('%2d:', i)
inner_enum = square_numbers(square_odd: outer_enum.peek)
3.times do
j = inner_enum.next[0]
printf(' %2d', j)
end
print("\n")
end

Writing Ruby inject method?

Im a bit confused at why this answer is "wrong" based on Ruby's own interpretation of the "Inject" method (for an array in this case, Im doing the "Odin Projects" projects for learning tasks)
def my_inject(start = nil)
memo = self[0] if start.nil?
for i in 0...self.length do
puts "#{memo}:#{self[i]} Results=#{yield(memo,self[i])}"
memo = yield(memo,self[i])
end
return memo
end
[5,6,7,8,9,10].my_inject { |sum, n| sum + n }
The Above returns this specifically:
5:5 Results=10
10:6 Results=16
16:7 Results=23
23:8 Results=31
31:9 Results=40
40:10 Results=50
=> 50
Which makes sense right? When no starting value is defined, the first value is used. However according to Ruby's API docs:"Inject" it should be 45....
Which doesn't make sense to me. We start with a memo of the first value and add it to the "elements" value. Which is 10 (in this case)...and so forth. Or are they saying when you DO NOT specify a value? you should skip the first array value?
I mean if I add up 5+6+7+8+9+10 yeah that is correctly 45, but if im doing what the block wants me to do, I feel like "50" makes more sense? Although obviously im wrong, im just not sure where.
I mean sure I could start the index off at 1 if we are not given a starting value...but that just seems odd.
Thanks
As people have pointed out in comments, your solution double taps the first element if no argument is provided.
Here's an implementation that is pretty straightforward, drops some unnecessary elements your solution included, and works for more than just arrays:
module Enumerable
def my_inject(memo = nil)
each { |x| memo = memo.nil? ? x : yield(memo, x) }
memo
end
end
p (1..5).my_inject(&:*) # 5 factorial => 120
p (1..5).my_inject(2, &:*) # 5 factorial doubled => 240
p %w(3 4 5).my_inject(&:+) # string concatenation => "345"
p %w(3 4 5).my_inject("hello", &:+) # concatenation w/ prefix => "hello345"
p %w(3 4 5).my_inject("howdy") { |memo, x| memo + x } # prefix and block => "howdy345"
ADDENDUM
If you want to go further and handle Symbol or String arguments as Enumerable#inject does, you need to do some preprocessing to determine what you're dealing with:
module Enumerable
def my_inject(memo = nil, sym = nil, &block)
memo = memo.to_sym if memo.is_a?(String) && !sym && !block
block, memo = memo.to_proc, nil if memo.is_a?(Symbol) && !sym
sym = sym.to_sym if sym.is_a?(String)
block = sym.to_proc if sym.is_a?(Symbol)
# Ready to rock & roll
each { |x| memo = memo.nil? ? x : block.yield(memo, x) }
memo
end
end
# A variety of test cases
p (1..4).my_inject(:*) # 4 factorial via Symbol => 24
p (1..5).my_inject('*') # 5 factorial via String => 120
p (1..6).my_inject { |memo, x| memo * x } # 6 factorial via block => 720
p (1..5).my_inject(2, &:*) # 5 factorial doubled via Proc => 240
p (1..5).my_inject(3, :*) # 5 factorial tripled via Symbol => 360
p (1..5).my_inject(4, '*') # 5 factorial quadrupled via String => 480
p %w(3 4 5).my_inject(&:+) # string concatenation via Proc => "345"
p %w(3 4 5).my_inject("hello", &:+) # prefix and Proc => "hello345"
p %w(3 4 5).my_inject("howdy") { |memo, x| memo + x } # prefix and block => "howdy345"
p %w(3 4 5).my_inject("yowza", :+) # prefix and Symbol => "yowza345"
p %w(3 4 5).my_inject("yoiks", '+') # prefix and String => "yoiks345"

Ruby lazy enumerator returning different object types depending on use

I was attempting to solve Project Euler #58 in a functional manner with ruby.
Briefly, I created an enumerator to return the corner number of each ring. I was then chaining functional operators on the enumerator. When I get my result, I find that it has a different class depending on how I use it.
spiral = Enumerator.new do |yielder|
n = 3
step = 2
loop do
vals = n.step(nil, step).take(4)
yielder.yield vals
step += 2
n = vals.last + step
end
end
primes = [2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101,103,107,109,113]
levels = spiral
.lazy
.map { |ring| ring.count { |n| primes.include? n } }
.with_object({:total=>1.0, :primes=>0})
.take_while do |ring_primes, counts|
counts[:total] += 4
counts[:primes] += ring_primes
(counts[:primes] / counts[:total]) > 0.5
end
The class of levels is a lazy enumerator. I would expect it to contain the number of primes in each ring [3, 2, 3, etc.] - see the project euler reference.
If I just print from the enumerator, I get what I expect:
levels.each do |level|
puts "#{level}"
end
Returns:
3
2
3
1
But if I loop .with_index I get an array result back where the expected value is the first member and the second is my .with_object parameter
levels.each.with_index do |level, ix|
puts "#{ix}: #{level}"
end
Returns:
0: [3, {:total=>5.0, :primes=>3}]
1: [2, {:total=>9.0, :primes=>5}]
2: [3, {:total=>13.0, :primes=>8}]
3: [1, {:total=>17.0, :primes=>9}]
Why does the lazy enumerator work this way and how could I predict for it in the future?
Update
I asked around on the IRC ruby channel and no one there had any idea about it. They said they had discussed it a day or two ago and hadn't come to any conclusions.
In general, it seems one must just deal with it and move on.
What's happening here is you're conveniently ignoring the structure that's returned and plucking out the first item to display. In this case the first item is the counts structure you produce.
Have a look at this:
levels.each do |*level|
puts level.inspect
end
That shows you what's actually in the levels results. When Ruby calls a lambda it will discard any additional data that doesn't fit with the number of arguments the block accepts.
If you don't need that metadata, strip it out:
levels = spiral
.lazy
.map { |ring| ring.count { |n| primes.include? n } }
.with_object({:total=>1.0, :primes=>0})
.take_while do |ring_primes, counts|
counts[:total] += 4
counts[:primes] += ring_primes
(counts[:primes] / counts[:total]) > 0.5
end
.map { |r,_| r }
That removes the extraneous element in the results.
Here's a way of cleaning up your Enumerator a bit:
class Spiral
include Enumerable
def each
Enumerator.new do |yielder|
n = 3
step = 2
loop do
vals = n.step(nil, step).take(4)
yielder.yield vals
step += 2
n = vals.last + step
end
end
end
end
Then you can create one with:
Spiral.new.each ...

Check if the sum of two different numbers in an array equal a variable number?

In Ruby, I would like to take an array of numbers, select 2 different numbers, add those 2 numbers together and see weather there equal to a variable x.y'd a variable x. Here is the code I used
def arrayIsEqual? (numArray, x)
return true if numArray.sample + numArray.sample == x
return false if numArray.empty? || numArray.count == 1
end
for example
numArray = [4,2,7,5]
x = 11
arrayIsEqual (numArray, n) should return true, since 4 + 7 = n(11)
How do I get this to work?
I don't want it to be 2 random numbers, just any 2 different numbers that add up to n
It looks like you're trying to see if there are any two numbers in the array that add up to the specified value x. However, your code just picks two numbers at random and checks if those numbers add up.
Ruby has the Array#combination method, which generates all combinations of a given length:
def contains_pair_for_sum?(arr, n)
!!arr.uniq.combination(2).detect { |a, b| a + b == n }
end
A few things to note:
First, we named it according to Ruby conventions: each word is separated_by_underscores. The ? on the end means that the method is a predicate method and returns a true or false value.
Inside the method, a few things happen. Let's look at that line, piece by piece.
arr: We take the array that was passed in.
<...>.uniq: We only look at the unique elements (because the OP wants to pick two different numbers).
<...>.combination(2): We ask for all combinations from the array of length 2. If the array was [4, 5, 6], we'd get [[4, 5], [4, 6], [5, 6]].
<...>.detect { |a, b| a + b == n }: We look for the first combination that adds up to n. If we found one, that's the result of that method. Otherwise, we get nil.
!!<...>: Finally, we take the result we got from detect and negate it twice. The first negation produces a Boolean value (true if the value we got was nil, or false if it's anything else); the second negation produces a Boolean value that's identical to the truth value of the first negation. This is a Ruby idiom to coerce a result into being either true or false.
Let's see it in action:
array = [4, 5, 9, 7, 8]
contains_pair_for_sum?(array, 11)
# => true (because [4, 7] sums to 11)
contains_pair_for_sum?(array, 17)
# => true (because [9, 8] sums to 17)
contains_pair_for_sum?(array, 100)
# => false (no pair matched)
I understand that your question is "is there any pair of numbers in my array equals x", in which case this will do what you need:
def has_pair_equal?(num_array, x)
(0..num_array.length-1).any? do |i|
num_array[i+1..-1].any? { |n| n + num_array[i] == x }
end
end
This checks all sums of pairs of numbers in the array, and checks if their sum is x. sample randomly picks an item from the array, which means that what your code does is "return true sometimes if there is a pair of numbers in my array equals x"
def array_is_equal? (num_array, x)
equality = 0
num_array.each do |a|
equality += 1 if a == x
return true if equality == 2
end
return false
end
Use lowercase and underscores for variables in Ruby. The convention is different here than in some other languages.
One liner
x=[4,2,7,5]; x.each_with_index.any? {|y,i| x.each_with_index.any? {|z,j| unless i==j; z+y==11; end } }
And as a function
def pair_sum_match?(arr, x)
arr.each_with_index.any? do |y,i|
arr.each_with_index.any? do |z,j|
unless i==j
z+y==x
end
end
end
end
Updated: Added each_with_index to avoid self inclusion on checks. It's a lot longer now :-/
Just iterate over it once and use the target number to see if it matches. 100 times faster then most of the answers here
numbers = ( -10..10 ).to_a
numbers.unshift( numbers.first + -1 ) # if you do -20 or 20
numbers.push( numbers.last + 1 )
target = 5
searched = { }
matches = { }
numbers.each do |number|
if searched[ target - number + 1 ] == true
matches[ "#{ number }_plus_#{ target - number }" ] = target
end
searched[ number + 1 ] = true
end
ap matches

Ruby: Overloading Yield Function

I noticed while learning Ruby that both of these uses of the each method work and produce the same output, and I was wondering how Ruby makes this happen (and how I can make it happen for my own functions):
my_array = [["hello","goodbye"],["picture","perfect"]]
my_array.each do |array|
puts array[0] + " " + array[1]
end
my_array.each do |first, second|
puts first + " " + second
end
My understanding is that when writing the definition of a method that accepts a code block, the yield method is utilized to pass arguments to the code block and call the block. But how can you utilize the yield method such that it passes different arguments depending on the provided code block? In the example case, it appears that the yield method passes the individual array elements when two parameters (i.e., first, second) are used within the block, and it passes the arrays themselves when one parameter is used within the block (i.e., array).
Neither each not yield are doing anything special here, that's just how block arguments work. Consider this simple example:
def f(x) yield x end
and now we can see what happens:
>> f([1,2]) { |a| puts a.inspect }
[1, 2]
>> f([1,2]) { |a, b| puts "#{a} - #{b}" }
1 - 2
>> f([1,2]) { |a, b, c| puts "#{a} - #{b} - #{c}" }
1 - 2 -
You'll see similar destructing in assignments:
a, b = [1, 2]
You can also do it explicitly with a splat:
a, b = *[1, 2]
or like this:
def g(x) yield *x end
g([1, 2]) { |a, b| puts "#{a} - #{b}" }
Presumably the block knows what sorts of things it will be given so the block is well positioned to unpack the arguments. Note that the g function has to know that its argument is splatable (i.e. an array) but f doesn't. f nicely puts the "what sort of thing is x" logic together in the call to f, g buries half of the logic inside itself. One place where the difference becomes apparent is when you use Enumerable methods on a Hash:
{ :where => :is, :pancakes => :house? }.map { |k, v| ... }
Enumerable#map doesn't need to know that a Hash works in key/value two element arrays, it just passes things around and leaves it up everyone else to worry about the details.

Resources