slide_rule 0.2.0 → 1.0.1

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
- SHA1:
3
- metadata.gz: d6f0cc115c650f57a1ebc32fb16dedb8647df5c4
4
- data.tar.gz: cf1f0ba21b49a34ebc56d7595366180adec9d744
2
+ SHA256:
3
+ metadata.gz: 38e1fef1daba59d9089c2d76e641bd3badbb63fc8f6ee41e1848a25d6c37ca97
4
+ data.tar.gz: c408e991827a4432a65635aac1a08ae4adfc85fbd7b6e07374db3521ea000a67
5
5
  SHA512:
6
- metadata.gz: 2fc5aff23287ff405bdc120e5378e48f3b10c30ef23bbd311766cf6cebd7b149dd0fcfc3a34e2fe94cbc45ffe0cbd8a5b6310f3e02031ead580922ff0ead0bba
7
- data.tar.gz: e8913245a2286590fa8e8560885ce86024506fc132424813187103a71de0e625532cea53edc59c476038e3be29c46af6d009a03f3c7d605c31ae23022d861f15
6
+ metadata.gz: ec65e2cdf24fe70bf839a8885ecb42cb40a958aa592fe7a1cf360bd6b7bb1462afcb13e675e0dcfbfd89c4f5dc063f8e240e457b2f1041daf08ee303336f373b
7
+ data.tar.gz: 7911f9ed6c7043eb623c80984820fddc02130d1ec5c74681204441d7c644d83d6432d2f87778abb5a64849b415105b261cb1a3722faf0ed2c91e3340bf0fc730
data/.gitignore CHANGED
@@ -2,3 +2,7 @@
2
2
  **.DS_Store
3
3
  Guardfile
4
4
  Gemfile.lock
5
+ vendor/cache
6
+ .ruby-gemset
7
+ .ruby-version
8
+ pkg/
data/.rubocop.yml CHANGED
@@ -1,3 +1,5 @@
1
+ inherit_from:
2
+ - config/rubocop/disabled.yml
1
3
  AllCops:
2
4
  DisplayCopNames: true
3
5
  Exclude:
data/README.md CHANGED
@@ -19,25 +19,26 @@ _Note: weights are assumed to be equal if not provided_
19
19
 
20
20
  #API
21
21
 
22
- ##Describe the field calculators
22
+ ##Describe the field distance calculators
23
23
 
24
24
  Each field to be considered in the distance calculation should be described
25
25
  with a calculation method and weight(optional)
26
26
 
27
27
  Valid calculators:
28
28
 
29
- * day_of_month (this needs to be factored into configurable date_recurrence)
30
- * float_range_distance
29
+ * day_of_year
30
+ * day_of_month
31
+ * levenshtein
31
32
 
32
33
  ```ruby
33
34
  distance_rules = {
34
35
  :description => {
35
36
  :weight => 0.80,
36
- :type => :levenshtein,
37
+ :calculator => :levenshtein,
37
38
  },
38
39
  :date => {
39
40
  :weight => 0.90,
40
- :type => :day_of_month,
41
+ :calculator => :day_of_month,
41
42
  },
42
43
  }
43
44
  ```
@@ -81,3 +82,41 @@ matcher.closest_match(candidate, [example, example2], 0.2)
81
82
  => example
82
83
 
83
84
  ```
85
+
86
+ ## Custom Field Distance Calculators
87
+
88
+ To define a custom field distance calculator, define a class with a `calculate(value1, value2)` method.
89
+
90
+ Requirements:
91
+ * Class must be stateless
92
+ * Calculate should return a float from `0` (perfect match) to `1.0` (no match)
93
+ * Calculation should not be order dependent (e.g. `calculate(a, b) == calculate(b, a)`)
94
+
95
+ ```ruby
96
+ class StringLengthCalculator
97
+ def calculate(l1, l2)
98
+ diff = (l1 - l2).abs.to_f
99
+ return diff / [l1, l2].max
100
+ end
101
+ end
102
+
103
+ matcher = ::SlideRule::DistanceCalculator.new(
104
+ :length => {
105
+ :weight => 1.0,
106
+ :calculator => StringLengthCalculator
107
+ }
108
+ )
109
+
110
+ # Find the string with the closest length
111
+ matcher.closest_match("Howdy Doody Time!", ["Felix the cat", "Mighty Mouse"], 0.5)
112
+ # => { :item=>"Mighty Mouse", :distance=>0.29411764705882354 }
113
+ ```
114
+
115
+ See the [distance_calculators](https://github.com/mattnichols/slide_rule/tree/master/lib/slide_rule/distance_calculators) directory in source for more examples.
116
+
117
+
118
+ # To Do
119
+
120
+ * Add more field distance calculators
121
+
122
+
@@ -0,0 +1,4 @@
1
+ Style/PredicateName:
2
+ Description: 'Check the names of predicate methods.'
3
+ StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#bool-methods-qmark'
4
+ Enabled: false
@@ -1,7 +1,9 @@
1
1
  module SlideRule
2
2
  class DistanceCalculator
3
+ attr_accessor :rules
4
+
3
5
  def initialize(rules)
4
- @rules = normalize_weights(rules)
6
+ @rules = prepare_rules(rules)
5
7
  end
6
8
 
7
9
  # TODO: Figure this out. Very inefficient!
@@ -20,8 +22,15 @@ module SlideRule
20
22
  end
21
23
  end
22
24
 
23
- def closest_match(obj, array, threshold)
24
- matches(obj, array, threshold).sort { |match| match[:distance] }.first
25
+ def closest_match(obj, array, threshold = 1.0)
26
+ matches(obj, array, threshold).sort_by { |match| match[:distance] }.first
27
+ end
28
+
29
+ def closest_matching_item(obj, array, threshold = 1.0)
30
+ match = closest_match(obj, array, threshold)
31
+ return nil if match.nil?
32
+
33
+ match[:item]
25
34
  end
26
35
 
27
36
  def is_match?(obj_1, obj_2, threshold)
@@ -32,7 +41,7 @@ module SlideRule
32
41
  def matches(obj, array, threshold)
33
42
  array.map do |item|
34
43
  distance = calculate_distance(obj, item)
35
- next nil unless distance < threshold
44
+ next nil unless distance <= threshold
36
45
  {
37
46
  item: item,
38
47
  distance: distance
@@ -48,23 +57,41 @@ module SlideRule
48
57
  # {
49
58
  # :attribute_name => {
50
59
  # :weight => 0.90,
51
- # :type => :distance_calculator,
60
+ # :calculator => :distance_calculator,
61
+ # :threshold => 30
52
62
  # }
53
63
  # }
54
64
  def calculate_distance(i1, i2)
55
- @rules.map do |attribute, rule|
65
+ calculate_weighted_distances(i1, i2).reduce(0.0) do |distance, obj|
66
+ distance + (obj[:distance] * obj[:weight])
67
+ end
68
+ end
69
+
70
+ private
71
+
72
+ def calculate_weighted_distances(i1, i2)
73
+ distances = @rules.map do |attribute, options|
56
74
  val1 = i1.send(attribute)
57
75
  val2 = i2.send(attribute)
58
- calculator = get_calculator(rule[:type])
59
- calculator.calculate(val1, val2).to_f * rule[:weight]
60
- end.reduce(0.0, &:+)
76
+ distance = options[:calculator].calculate(val1, val2, options)
77
+ next { distance: distance.to_f, weight: options[:weight] } unless distance.nil?
78
+
79
+ nil
80
+ end
81
+ normalize_weights_array(distances) if distances.compact!
82
+
83
+ distances
61
84
  end
62
85
 
63
86
  def get_calculator(calculator)
64
87
  return calculator.new if calculator.is_a?(Class)
65
88
 
66
- klass_name = "#{calculator.to_s.split('_').collect(&:capitalize).join}"
67
- klass = ::SlideRule::DistanceCalculators.const_get(klass_name)
89
+ klass_name = calculator.to_s.split('_').collect(&:capitalize).join.to_s
90
+ klass = begin
91
+ ::SlideRule::DistanceCalculators.const_get(klass_name)
92
+ rescue ::NameError
93
+ nil
94
+ end
68
95
 
69
96
  fail ArgumentError, "Unable to find calculator #{klass_name}" if klass.nil?
70
97
 
@@ -73,12 +100,46 @@ module SlideRule
73
100
 
74
101
  # Ensures all weights add up to 1.0
75
102
  #
76
- def normalize_weights(rules_hash)
77
- rules = rules_hash.dup
103
+ def normalize_weights(rules)
78
104
  weight_total = rules.map { |_attr, rule| rule[:weight] }.reduce(0.0, &:+)
79
105
  rules.each do |_attr, rule|
80
106
  rule[:weight] = rule[:weight] / weight_total
81
107
  end
82
108
  end
109
+
110
+ # Ensures all weights add up to 1.0 in array of hashes
111
+ #
112
+ def normalize_weights_array(rules)
113
+ weight_total = rules.map { |rule| rule[:weight] }.reduce(0.0, &:+)
114
+ rules.each do |rule|
115
+ rule[:weight] = rule[:weight] / weight_total
116
+ end
117
+ end
118
+
119
+ # Prepares a duplicate of given rules hash with normalized weights and calculator instances
120
+ #
121
+ def prepare_rules(rules)
122
+ prepared_rules = rules.each_with_object({}) do |(attribute, rule), copy|
123
+ rule = copy[attribute] = safe_dup(rule)
124
+
125
+ if rule[:type]
126
+ puts 'Rule key `:type` is deprecated. Use `:calculator` instead.'
127
+ rule[:calculator] = rule[:type]
128
+ end
129
+
130
+ rule[:calculator] = get_calculator(rule[:calculator])
131
+
132
+ copy
133
+ end
134
+ prepared_rules = normalize_weights(prepared_rules)
135
+
136
+ prepared_rules
137
+ end
138
+
139
+ def safe_dup(obj)
140
+ obj.dup
141
+ rescue
142
+ obj
143
+ end
83
144
  end
84
145
  end
@@ -7,7 +7,8 @@ module SlideRule
7
7
  # Calculates distance using 15 as the max point.
8
8
  # Does not take into account the number of days in the actual month being considered.
9
9
  #
10
- def calculate(first, second)
10
+ def calculate(first, second, options={})
11
+ return nil if first.nil? || second.nil?
11
12
  first = cleanse_date(first)
12
13
  second = cleanse_date(second)
13
14
 
@@ -23,6 +24,7 @@ module SlideRule
23
24
  private
24
25
 
25
26
  def cleanse_date(date)
27
+ date = Time.at(date).utc.to_date if date.is_a?(::Integer)
26
28
  date = Date.parse(date) unless date.is_a?(::Date) || date.is_a?(::Time)
27
29
  date = date.to_date if date.is_a?(::Time)
28
30
 
@@ -3,21 +3,22 @@ module SlideRule
3
3
  class DayOfYear
4
4
  DAYS_IN_YEAR = 365
5
5
 
6
- def calculate(date_1, date_2)
6
+ def calculate(date_1, date_2, options={})
7
7
  date_1 = cleanse_date(date_1)
8
8
  date_2 = cleanse_date(date_2)
9
-
9
+ threshold = options[:threshold] || DAYS_IN_YEAR
10
10
  days_apart = (date_1.mjd - date_2.mjd).abs
11
11
 
12
- return 1 if days_apart >= DAYS_IN_YEAR
12
+ return 1 if days_apart >= threshold
13
13
 
14
- distance = days_apart.to_f / DAYS_IN_YEAR
14
+ distance = days_apart.to_f / threshold
15
15
  distance.round(2)
16
16
  end
17
17
 
18
18
  private
19
19
 
20
20
  def cleanse_date(date)
21
+ date = Time.at(date).utc.to_date if date.is_a?(::Integer)
21
22
  date = Date.parse(date) unless date.is_a?(::Date) || date.is_a?(::Time)
22
23
  date = date.to_date if date.is_a?(::Time)
23
24
 
@@ -1,7 +1,7 @@
1
1
  module SlideRule
2
2
  module DistanceCalculators
3
3
  class Levenshtein
4
- def calculate(first, second)
4
+ def calculate(first, second, options={})
5
5
  ::Vladlev.get_normalized_distance(first, second).to_f
6
6
 
7
7
  # Lower bound is difference in length
@@ -1,3 +1,3 @@
1
1
  module SlideRule
2
- VERSION = '0.2.0'
2
+ VERSION = '1.0.1'.freeze
3
3
  end
data/slide_rule.gemspec CHANGED
@@ -7,7 +7,7 @@ Gem::Specification.new do |s|
7
7
  s.version = ::SlideRule::VERSION
8
8
  s.authors = %w(mattnichols fergmastaflex)
9
9
  s.email = ['dev@mx.com']
10
- s.homepage = 'https://github.com/mattnichols/slide_rule'
10
+ s.homepage = 'https://github.com/mxenabled/slide_rule'
11
11
  s.summary = 'Ruby object distance calculator'
12
12
  s.description = 'Calculates the distance between 2 arbitrary objects using specified fields and algorithms.'
13
13
  s.license = 'MIT'
@@ -14,11 +14,17 @@ describe ::SlideRule::DistanceCalculator do
14
14
  end
15
15
 
16
16
  class CustomCalc
17
- def calculate(_first, _second)
17
+ def calculate(_first, _second, _options)
18
18
  0.9
19
19
  end
20
20
  end
21
21
 
22
+ class NilCalc
23
+ def calculate(_first, _second, _options)
24
+ nil
25
+ end
26
+ end
27
+
22
28
  let(:examples) do
23
29
  [
24
30
  ::ExampleTransaction.new(amount: 25.00, date: '2015-02-05', description: 'Audible.com'),
@@ -36,22 +42,32 @@ describe ::SlideRule::DistanceCalculator do
36
42
  ::SlideRule::DistanceCalculator.new(
37
43
  description: {
38
44
  weight: 0.80,
39
- type: :levenshtein
45
+ calculator: :levenshtein
40
46
  },
41
47
  date: {
42
48
  weight: 0.90,
43
- type: :day_of_month
49
+ calculator: :day_of_month
44
50
  }
45
51
  )
46
52
  end
47
53
 
48
- it 'finds recurring transaction' do
54
+ it 'finds closest' do
49
55
  example = ExampleTransaction.new(description: 'Wells Fargo Dealer SVC', date: '2015-06-17')
50
56
  expect(calculator.closest_match(example, examples, 0.2)[:item]).to eq(examples[3])
51
57
 
52
58
  example = ExampleTransaction.new(description: 'Audible.com', date: '2015-06-05')
53
59
  expect(calculator.closest_match(example, examples, 0.2)[:item]).to eq(examples[0])
54
60
  end
61
+
62
+ it 'with default threshold' do
63
+ example = ExampleTransaction.new(description: 'Audible.com', date: '2015-06-05')
64
+ expect(calculator.closest_match(example, examples)[:item]).to eq(examples[0])
65
+ end
66
+
67
+ it 'finds closest matching item' do
68
+ example = ExampleTransaction.new(description: 'Audible.com', date: '2015-06-05')
69
+ expect(calculator.closest_matching_item(example, examples)).to eq(examples[0])
70
+ end
55
71
  end
56
72
 
57
73
  describe '#is_match?' do
@@ -59,23 +75,23 @@ describe ::SlideRule::DistanceCalculator do
59
75
  ::SlideRule::DistanceCalculator.new(
60
76
  description: {
61
77
  weight: 0.80,
62
- type: :levenshtein
78
+ calculator: :levenshtein
63
79
  },
64
80
  date: {
65
81
  weight: 0.90,
66
- type: :day_of_month
82
+ calculator: :day_of_month
67
83
  }
68
84
  )
69
85
  end
70
86
 
71
- it 'returns true if there is a match' do
87
+ it 'returns true if there is a match' do
72
88
  example_1 = ExampleTransaction.new(description: 'Wells Fargo Dealer SVC', date: '2015-06-17')
73
89
  example_2 = ExampleTransaction.new(description: 'Wells Fargo Dealer SVC', date: '2015-06-17')
74
90
 
75
91
  expect(calculator.is_match?(example_1, example_2, 0.2)).to be(true)
76
92
  end
77
93
 
78
- it 'returns false if there is a match' do
94
+ it 'returns false if there is a match' do
79
95
  example_1 = ExampleTransaction.new(description: 'Wells Fargo Dealer SVC', date: '2015-06-17')
80
96
  example_2 = ExampleTransaction.new(description: 'Taco Bell', date: '2015-06-17')
81
97
 
@@ -89,11 +105,11 @@ describe ::SlideRule::DistanceCalculator do
89
105
  calculator = ::SlideRule::DistanceCalculator.new(
90
106
  description: {
91
107
  weight: 1.00,
92
- type: :levenshtein
108
+ calculator: :levenshtein
93
109
  },
94
110
  date: {
95
111
  weight: 0.50,
96
- type: :day_of_month
112
+ calculator: :day_of_month
97
113
  }
98
114
  )
99
115
  example = ::ExampleTransaction.new(amount: 25.00, date: '2015-02-05', description: 'Audible.com')
@@ -105,11 +121,11 @@ describe ::SlideRule::DistanceCalculator do
105
121
  calculator = ::SlideRule::DistanceCalculator.new(
106
122
  description: {
107
123
  weight: 0.50,
108
- type: :levenshtein
124
+ calculator: :levenshtein
109
125
  },
110
126
  date: {
111
127
  weight: 0.50,
112
- type: :day_of_month
128
+ calculator: :day_of_month
113
129
  }
114
130
  )
115
131
  example = ::ExampleTransaction.new(amount: 25.00, date: '2015-02-05', description: 'Audible.com')
@@ -125,6 +141,23 @@ describe ::SlideRule::DistanceCalculator do
125
141
  distance = calculator.calculate_distance(example, candidate)
126
142
  expect(distance.round(4)).to eq(((3.0 * 0.5 / 15) + (4.0 * 0.5 / 11)).round(4))
127
143
  end
144
+
145
+ it 'should renormalize on nil' do
146
+ calculator = ::SlideRule::DistanceCalculator.new(
147
+ description: {
148
+ weight: 0.50,
149
+ calculator: :levenshtein
150
+ },
151
+ date: {
152
+ weight: 0.50,
153
+ calculator: NilCalc
154
+ }
155
+ )
156
+ example1 = ::ExampleTransaction.new(amount: 25.00, date: '2015-02-05', description: 'Audible.com')
157
+ example2 = ::ExampleTransaction.new(amount: 25.00, date: '2015-06-08', description: 'Audible Inc')
158
+
159
+ expect(calculator.calculate_distance(example1, example2).round(4)).to eq((4.0 / 11).round(4))
160
+ end
128
161
  end
129
162
 
130
163
  context 'uses custom calculator' do
@@ -132,7 +165,7 @@ describe ::SlideRule::DistanceCalculator do
132
165
  calculator = ::SlideRule::DistanceCalculator.new(
133
166
  description: {
134
167
  weight: 1.00,
135
- type: CustomCalc
168
+ calculator: CustomCalc
136
169
  }
137
170
  )
138
171
  example = ::ExampleTransaction.new
@@ -142,5 +175,51 @@ describe ::SlideRule::DistanceCalculator do
142
175
  expect(distance).to eq(0.9)
143
176
  end
144
177
  end
178
+
179
+ describe '#initialize' do
180
+ context 'validates rules on initialize' do
181
+ it 'should allow :type' do
182
+ ::SlideRule::DistanceCalculator.new(
183
+ description: {
184
+ weight: 1.00,
185
+ type: CustomCalc
186
+ }
187
+ )
188
+ end
189
+
190
+ it 'should not modify input rule hash' do
191
+ rules = {
192
+ description: {
193
+ weight: 1.0,
194
+ type: CustomCalc
195
+ },
196
+ name: {
197
+ weight: 1.0,
198
+ type: CustomCalc
199
+ }
200
+ }
201
+ ::SlideRule::DistanceCalculator.new(rules)
202
+ # Run a second time to ensure that no calculator instance is in rules. Will currently throw an error.
203
+ ::SlideRule::DistanceCalculator.new(rules)
204
+
205
+ # :type should still be in original hash
206
+ expect(rules[:name].key?(:calculator)).to eq(false)
207
+
208
+ # :weight should not be normalized in original hash
209
+ expect(rules[:name][:weight]).to eq(1.0)
210
+ end
211
+
212
+ it 'should raise error if not valid calculator' do
213
+ expect do
214
+ ::SlideRule::DistanceCalculator.new(
215
+ description: {
216
+ weight: 1.00,
217
+ calculator: :some_junk
218
+ }
219
+ )
220
+ end.to raise_error(::ArgumentError, 'Unable to find calculator SomeJunk')
221
+ end
222
+ end
223
+ end
145
224
  end
146
225
  end
@@ -1,4 +1,5 @@
1
1
  require 'spec_helper'
2
+ require 'date'
2
3
 
3
4
  describe ::SlideRule::DistanceCalculators::DayOfMonth do
4
5
  describe '#calculate' do
@@ -6,6 +7,10 @@ describe ::SlideRule::DistanceCalculators::DayOfMonth do
6
7
  expect(described_class.new.calculate('2012-03-19', '2014-08-19')).to eq(0.0)
7
8
  end
8
9
 
10
+ it 'should accept epoch date' do
11
+ expect(described_class.new.calculate(1_444_262_400, 1_444_262_400)).to eq(0.0)
12
+ end
13
+
9
14
  it 'should calculate when date is in the same month' do
10
15
  expect(described_class.new.calculate('2012-03-19', '2014-08-22')).to eq(3.0 / 15)
11
16
  expect(described_class.new.calculate('2012-03-19', '2014-08-09')).to eq(10.0 / 15)
@@ -5,6 +5,10 @@ describe ::SlideRule::DistanceCalculators::DayOfYear do
5
5
  it 'should return a 0 distance' do
6
6
  expect(described_class.new.calculate('2015-10-8', '2015-10-8')).to eq(0.0)
7
7
  end
8
+
9
+ it 'should accept epoch date' do
10
+ expect(described_class.new.calculate(1_444_262_400, 1_444_262_400)).to eq(0.0)
11
+ end
8
12
  end
9
13
 
10
14
  context 'when dates are more than a year apart' do
@@ -18,4 +22,17 @@ describe ::SlideRule::DistanceCalculators::DayOfYear do
18
22
  expect(described_class.new.calculate('2015-10-8', '2015-11-8')).to eq(0.08)
19
23
  end
20
24
  end
25
+
26
+ context 'when there is a threshold' do
27
+ it 'should return a 1 distance when there are too many days apart' do
28
+ expect(described_class.new.calculate('2016-02-03', '2016-03-09', :threshold => 30)).to eq(1)
29
+ end
30
+
31
+ it 'should return a more sane number' do
32
+ result_with_threshold = described_class.new.calculate('2016-02-03', '2016-02-10', :threshold => 30)
33
+ result_without_threshold = described_class.new.calculate('2016-02-03', '2016-02-10')
34
+
35
+ expect(result_with_threshold).to be > result_without_threshold
36
+ end
37
+ end
21
38
  end
@@ -1,11 +1,19 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe ::SlideRule::DistanceCalculators::Levenshtein do
4
+ let(:subject) { described_class.new }
5
+
4
6
  it 'should calculate perfect match' do
5
- expect(described_class.new.calculate('this is a test', 'this is a test')).to eq(0.0)
7
+ expect(subject.calculate('this is a test', 'this is a test')).to eq(0.0)
6
8
  end
7
9
 
8
10
  it 'should calculate distance as distance divided by length of longest string' do
9
- expect(described_class.new.calculate('this is a test', 'this is a test!').round(4)).to eq((1.0 / 15).round(4))
11
+ expect(subject.calculate('this is a test', 'this is a test!').round(4)).to eq((1.0 / 15).round(4))
12
+ end
13
+
14
+ it 'should handle nils' do
15
+ expect(subject.calculate(nil, nil)).to eq(0.0)
16
+ expect(subject.calculate(nil, 'goodbye')).to eq(1.0)
17
+ expect(subject.calculate('hello', nil)).to eq(1.0)
10
18
  end
11
19
  end
data/spec/spec_helper.rb CHANGED
@@ -18,6 +18,7 @@
18
18
  # See http://rubydoc.info/gems/rspec-core/RSpec/Core/Configuration
19
19
 
20
20
  require_relative '../lib/slide_rule.rb'
21
+ require 'pry'
21
22
 
22
23
  RSpec.configure do |config|
23
24
  # rspec-expectations config goes here. You can use an alternate
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: slide_rule
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 1.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - mattnichols
@@ -9,12 +9,12 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2016-01-11 00:00:00.000000000 Z
12
+ date: 2021-08-26 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  requirement: !ruby/object:Gem::Requirement
16
16
  requirements:
17
- - - ~>
17
+ - - "~>"
18
18
  - !ruby/object:Gem::Version
19
19
  version: '1.0'
20
20
  name: vladlev
@@ -22,13 +22,13 @@ dependencies:
22
22
  type: :runtime
23
23
  version_requirements: !ruby/object:Gem::Requirement
24
24
  requirements:
25
- - - ~>
25
+ - - "~>"
26
26
  - !ruby/object:Gem::Version
27
27
  version: '1.0'
28
28
  - !ruby/object:Gem::Dependency
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
- - - ~>
31
+ - - "~>"
32
32
  - !ruby/object:Gem::Version
33
33
  version: '10'
34
34
  name: rake
@@ -36,13 +36,13 @@ dependencies:
36
36
  type: :development
37
37
  version_requirements: !ruby/object:Gem::Requirement
38
38
  requirements:
39
- - - ~>
39
+ - - "~>"
40
40
  - !ruby/object:Gem::Version
41
41
  version: '10'
42
42
  - !ruby/object:Gem::Dependency
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
- - - ~>
45
+ - - "~>"
46
46
  - !ruby/object:Gem::Version
47
47
  version: '0'
48
48
  name: pry
@@ -50,13 +50,13 @@ dependencies:
50
50
  type: :development
51
51
  version_requirements: !ruby/object:Gem::Requirement
52
52
  requirements:
53
- - - ~>
53
+ - - "~>"
54
54
  - !ruby/object:Gem::Version
55
55
  version: '0'
56
56
  - !ruby/object:Gem::Dependency
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
- - - ~>
59
+ - - "~>"
60
60
  - !ruby/object:Gem::Version
61
61
  version: '3'
62
62
  name: rspec
@@ -64,13 +64,13 @@ dependencies:
64
64
  type: :development
65
65
  version_requirements: !ruby/object:Gem::Requirement
66
66
  requirements:
67
- - - ~>
67
+ - - "~>"
68
68
  - !ruby/object:Gem::Version
69
69
  version: '3'
70
70
  - !ruby/object:Gem::Dependency
71
71
  requirement: !ruby/object:Gem::Requirement
72
72
  requirements:
73
- - - ~>
73
+ - - "~>"
74
74
  - !ruby/object:Gem::Version
75
75
  version: '0'
76
76
  name: rubocop
@@ -78,24 +78,26 @@ dependencies:
78
78
  type: :development
79
79
  version_requirements: !ruby/object:Gem::Requirement
80
80
  requirements:
81
- - - ~>
81
+ - - "~>"
82
82
  - !ruby/object:Gem::Version
83
83
  version: '0'
84
- description: Calculates the distance between 2 arbitrary objects using specified fields and algorithms.
84
+ description: Calculates the distance between 2 arbitrary objects using specified fields
85
+ and algorithms.
85
86
  email:
86
87
  - dev@mx.com
87
88
  executables: []
88
89
  extensions: []
89
90
  extra_rdoc_files: []
90
91
  files:
91
- - .gitignore
92
- - .rubocop.yml
93
- - .travis.yml
92
+ - ".gitignore"
93
+ - ".rubocop.yml"
94
+ - ".travis.yml"
94
95
  - CODE_OF_CONDUCT.md
95
96
  - Gemfile
96
97
  - LICENSE
97
98
  - README.md
98
99
  - Rakefile
100
+ - config/rubocop/disabled.yml
99
101
  - lib/slide_rule.rb
100
102
  - lib/slide_rule/distance_calculator.rb
101
103
  - lib/slide_rule/distance_calculators/day_of_month.rb
@@ -108,7 +110,7 @@ files:
108
110
  - spec/slide_rule/distance_calculators/day_of_year_spec.rb
109
111
  - spec/slide_rule/distance_calculators/levenshtein_spec.rb
110
112
  - spec/spec_helper.rb
111
- homepage: https://github.com/mattnichols/slide_rule
113
+ homepage: https://github.com/mxenabled/slide_rule
112
114
  licenses:
113
115
  - MIT
114
116
  metadata: {}
@@ -118,17 +120,16 @@ require_paths:
118
120
  - lib
119
121
  required_ruby_version: !ruby/object:Gem::Requirement
120
122
  requirements:
121
- - - '>='
123
+ - - ">="
122
124
  - !ruby/object:Gem::Version
123
125
  version: '0'
124
126
  required_rubygems_version: !ruby/object:Gem::Requirement
125
127
  requirements:
126
- - - '>='
128
+ - - ">="
127
129
  - !ruby/object:Gem::Version
128
130
  version: '0'
129
131
  requirements: []
130
- rubyforge_project:
131
- rubygems_version: 2.4.8
132
+ rubygems_version: 3.2.15
132
133
  signing_key:
133
134
  specification_version: 4
134
135
  summary: Ruby object distance calculator