defmatch 0.0.2 → 0.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 808ffbab0823cd56fcf58947e9a4069a9a0eaace
4
- data.tar.gz: 24a6775f4a3104fd9e8eb11dccfac5994d32c38f
3
+ metadata.gz: 31f145fc6e1eb79e17023f0857c7aa0743d21635
4
+ data.tar.gz: ee52c39e0f841cc70ef1724453b524084463b88a
5
5
  SHA512:
6
- metadata.gz: a2f969d8e6555eeca144d12a147c78bdeb09032aecd05c18e4bcea029c548811836f881ead8e66a438d2f3db06eb7de557c2d6e38097e5f539debd3d6bb50da7
7
- data.tar.gz: ec2832a06d1851b00105e4dbc52b4f09a66ea14942e42fc4f1c9e08d3d48fc9d56f9a910b01bcc2a362e0f4f3ae7177f21d84eeb40632170aa85f0e8d28d990c
6
+ metadata.gz: 28cb8b2f285d1befe9ec3e5fea7be53e5c55244499f497a976463ce2662fd79dc42eb610e7e95026ed3af2318428d4cbd282af4736817053c37f3a74f39ad2ee
7
+ data.tar.gz: f33a33c7ac4dd4bbe779d3c056bf0e2c39ebc7f2925f978cefa39b2a259be92e092427ea8c0c09d658398055968cf128ffa334fae16d77390fd318107bd4d142
data/README.md CHANGED
@@ -85,6 +85,5 @@ Even if I run ```x.magic(1)``` I will get ```2``` as the result. The second defm
85
85
 
86
86
  ## Roadmap
87
87
 
88
- * Add defclassmatch for class methods
89
88
  * Add parameter deconstruction
90
89
  * Add it to the Kernel so it's available without having to include things. This will require ruby 2.0 and I'm not prepared to kill backwards compatability yet.
@@ -1,3 +1,3 @@
1
1
  module Defmatch
2
- VERSION = "0.0.2"
2
+ VERSION = "0.0.3"
3
3
  end
data/lib/defmatch.rb CHANGED
@@ -10,25 +10,36 @@ module Defmatch
10
10
  lambda {|param| param == arg }
11
11
  end
12
12
  end
13
- lambda do |*args|
14
- test = true;
15
- param_test_pairs = args.zip(tests)
16
- param_test_pairs.each {|pair| if (pair[1].nil? or (pair[1].call(pair[0]) == false)); test = false; break; end; }
17
- return test
13
+ lambda do |*targs|
14
+ if targs.size != tests.size # short circuit any testing if the airity doesn't match
15
+ return false
16
+ elsif targs.size > 0 # when the airity matches and there are arguments run the tests
17
+ test = true;
18
+ param_test_pairs = targs.zip(tests)
19
+ param_test_pairs.each {|pair| if (pair[1].nil? or (pair[1].call(pair[0]) == false)); test = false; break; end; }
20
+ return test
21
+ elsif tests.size == 0 # When arguments given are empty and the tests array is empty
22
+ return true
23
+ else # When the arguments given are empty but the tests array is Not empty
24
+ return false
25
+ end
18
26
  end
19
27
  end
20
28
 
21
29
  def defmatch(method,*args,&block)
22
30
  @defmatch_dispatch_info ||= {} # setup the methods in an instance variable
23
31
  @defmatch_dispatch_info[method] ||= [] # setup the ordered array for the method the first time
24
- @defmatch_dispatch_info[method] << {:test => Defmatch.signiture_match(method,args), :block => block} # add the hash for the test proc and the run proc (block given) to the list of matchers
32
+ # add the hash for the test proc and the run proc (block given) to the list of matchers
33
+ @defmatch_dispatch_info[method] << {
34
+ :test => Defmatch.signiture_match(method,args),
35
+ :block => block}
25
36
 
26
37
  # define dispatch method the first time
27
- unless respond_to?(method)
38
+ unless self.instance_methods.include?(method)
28
39
  self.send(:define_method,method) do |*args|
29
40
  self.class.instance_variable_get(:@defmatch_dispatch_info)[method].each do |hash|
30
41
  if hash[:test].call(*args)
31
- return self.instance_exec(*args,&hash[:block])
42
+ return self.instance_exec(*args,&hash[:block])
32
43
  end
33
44
  end
34
45
  raise ArgumentError, "No function clause matching arguments"
@@ -37,5 +48,26 @@ module Defmatch
37
48
 
38
49
  end
39
50
 
40
- end
51
+ # Lost of duplication between this and defmatch, but the rule is 1,2,n and we haven't hit n
52
+ def defclassmatch(method,*args,&block)
53
+ @defclassmatch_dispatch_info ||= {} # setup the methods in an instance variable
54
+ @defclassmatch_dispatch_info[method] ||= [] # setup the ordered array for the method the first time
55
+ @defclassmatch_dispatch_info[method] << {:test => Defmatch.signiture_match(method,args), :block => block} # add the hash for the test proc and the run proc (block given) to the list of matchers
56
+
57
+ # define dispatch method the first time
58
+ unless respond_to?(method)
59
+ eigenclass = class << self; self; end
60
+ eigenclass.instance_eval do
61
+ define_method(method) do |*args|
62
+ self.instance_variable_get(:@defclassmatch_dispatch_info)[method].each do |hash|
63
+ if hash[:test].call(*args)
64
+ return self.instance_exec(*args,&hash[:block])
65
+ end
66
+ end
67
+ raise ArgumentError, "No function clause matching arguments"
68
+ end
69
+ end
70
+ end
71
+ end
41
72
 
73
+ end
@@ -11,20 +11,42 @@ describe Defmatch do
11
11
  defmatch(:times,1) {|num| puts "this should never get run"; num }
12
12
  defmatch(:times,"matchme") {|string| "matched literal #{string}" }
13
13
  defmatch(:times,String) {|string| string*2 }
14
+ defmatch(:times) { "no args" }
15
+
16
+ defmatch(:scope) { self }
17
+
18
+ defclassmatch(:cscope) { self }
14
19
  end
15
20
 
16
- it 'creates a method' do
21
+ it 'should create methods' do
17
22
  expect(Tester).to respond_to(:defmatch)
23
+ expect(Tester).to respond_to(:defclassmatch)
18
24
  end
19
25
 
20
26
  it 'should have an instance method "times"' do
21
27
  expect(Tester.new).to respond_to(:times)
22
28
  end
23
29
 
30
+ it 'should have an instance method "scope"' do
31
+ expect(Tester.new).to respond_to(:scope)
32
+ end
33
+
34
+ it 'should have a class method "cscope"' do
35
+ expect(Tester).to respond_to(:cscope)
36
+ end
37
+
38
+ it '\'s blocks should have the proper scope' do
39
+ expect(Tester.cscope).to equal(Tester)
40
+ end
41
+
24
42
  instance = Tester.new
25
43
 
26
44
  describe instance do
27
45
 
46
+ it '\'s blocks should have the correct scope' do
47
+ expect(instance.scope).to equal(instance)
48
+ end
49
+
28
50
  it 'should handle an integer' do
29
51
  expect(instance.times(4)).to equal(8)
30
52
  end
@@ -33,6 +55,10 @@ describe Defmatch do
33
55
  expect(instance.times([1,2,3,4])).to eq([2,4,6,8])
34
56
  end
35
57
 
58
+ it 'should handle a string' do
59
+ expect(instance.times("a")).to eq("aa")
60
+ end
61
+
36
62
  it 'should match a basic proc matcher' do
37
63
  expect(instance.times(:asdf)).to equal(:asdf)
38
64
  end
@@ -41,6 +67,10 @@ describe Defmatch do
41
67
  expect(instance.times("matchme")).to eq("matched literal matchme")
42
68
  end
43
69
 
70
+ it 'should match on no arguments' do
71
+ expect(instance.times).to eq("no args")
72
+ end
73
+
44
74
  it 'should run the first valid match based on defmatch declaration order' do
45
75
  expect(instance.times(1)).to equal(2)
46
76
  expect(instance.times("matchme")).to eq("matched literal matchme")
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: defmatch
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.2
4
+ version: 0.0.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Max Warnock