-
-
Save anonymous/2b6369fea84ae625c9bb to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# here is an expectation that utilizes a custom RSpec matcher, yield_variables: | |
specify { expect{ |p| [3,4,5].my_each(&p) }.to yield_variables [3,4,5] } | |
# my yield_variables matcher's matches? method utilizes a custom class called Probe: | |
... | |
def matches? block | |
ap Probe.probe block | |
# note i am inspecting what is returned by Probe.probe with ap | |
end | |
... | |
class Probe | |
attr_accessor :yielded_args | |
def initialize | |
self.yielded_args = [] | |
end | |
def self.probe(block) | |
probe = new | |
block.call(probe) | |
probe.yielded_args | |
end | |
def to_proc | |
Proc.new { |*args| yielded_args << args } | |
end | |
end | |
# now my ap inside matches? reports this: [3,4,5] That is what I expect. However, I have no idea how the Probe class works!! | |
# Problem 1) the matches? block | |
# Normally, the argument we pass to matches? is what we expect the subject to return. i.e, I expect [3,4,5] to be | |
# passed into block. | |
# Instead, |p| [3,4,5].my_each(&p) is passed into block, as a proc. Why is this? | |
# Problem 2) block.call(probe) | |
# I'm a bit shakey on procs so please explain slowly. But basically, here we take a new instance of my Probe class and 'send' the # block to it, as an argument. That's how I'd explain it to the best of my abilities, but I might have it totally wrong so please # explain slowly. | |
# Problem 3) How is to_proc called? | |
# How on earth is .to_proc called automatically? I believe it's called automatically by block.call(probe). Is to_proc an | |
# automatically called method like initialize? Is it automatically called whenever the class is sent to a proc? (Btw, the | |
# phrase the class is sent to a proc doesn't even make 100% sense to me - please explain. Like, the block isn't passed into | |
# the class as an # # argument anymore. Or if the block is passed as an argument the block.call syntax feels really weird and | |
# backwards) | |
# Problem 4) to_proc | |
# How does to_proc have access to the expectation's subject i.e. |p| [3,4,5].my_each(&p) ? How is Proc.new 's *args automatically # populated with every single possible yield argument, even though I've only passed in |p| ? How does **Proc.new loop along with | |
# my my_each, incrementally placing all my args in an array?** How does Proc.new have any knowledge | |
# of the subject |p| [3,4,5].my_each(&p) ? How?? Explain please, and thanks, I know this is a bit of an ask. |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment