fraction-tree 1.0.2 → 1.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/fraction_tree.rb +49 -10
  3. metadata +17 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 9d7d96a7fc5bfda274cc147d53e623984fc518de2fbfd3c5454df3d493ea5e44
4
- data.tar.gz: 900b7e263cc5df52e6c90932266a647d3e954e67e1dc3ea750f2d79d7d2b99ea
3
+ metadata.gz: 9d4c2e3c84acc2fa31151b2863bf7c602490e891004198884e8002a7b7f3cc32
4
+ data.tar.gz: c335d6bfb3f54c8471835cbc9283d904f8d71f7786cfde02a41448a1840ecb02
5
5
  SHA512:
6
- metadata.gz: '033058a25b6ab000b1657dd9f76d798969182b394e497ecbf3c220e6d15ae647947e52d5a7a4f16668162a8efd3327da70c3452b787b178962f27e0e0306fd46'
7
- data.tar.gz: 89544cc386de3e45b465294dc1fed8b83429882aa68662ec8e17d5feee149fce7817786ed1e8205f91bbeaed524ebfdac9f2c57a0d78f3853f0b2d6eb961d248
6
+ metadata.gz: ef4347b24418118dbf6f4c8fdc6ac03829829aaf5c15d51295befda2f6bddad1b7022b7b428906998ab2a18106a68850dacdc61c3616a345d911f5db32008c86
7
+ data.tar.gz: 940a05ae9a163d32cae321457da5135334f8a45a96bd0a6141d420d133216c912cd50826c33c3488fa7c17c96286ec11e755e2c8199afe4cddc8fee9846e25bf
data/lib/fraction_tree.rb CHANGED
@@ -1,3 +1,4 @@
1
+ require "bigdecimal/util"
1
2
  require "continued_fractions"
2
3
 
3
4
  # @author Jose Hales-Garcia
@@ -66,6 +67,8 @@ class FractionTree
66
67
  #
67
68
  def path_to(number, find_parents: false, segment: base_segment)
68
69
  return Node.new(number.numerator, number.denominator) if number.zero?
70
+ number = number.kind_of?(Float) ? number.to_d : number
71
+
69
72
  q = Node.new(number.numerator, number.denominator)
70
73
  l = segment.first
71
74
  h = segment.last
@@ -200,6 +203,37 @@ class FractionTree
200
203
  end
201
204
  end
202
205
 
206
+ # @return [Array] of Farey neighbors to the given number. A Farey neighbor is a number b/c, who's relationship to a/b is such that ad − bc = 1, when c/d < a/b and bc − ad = 1 when c/d > a/b.
207
+ # @example
208
+ # FractionTree.farey_neighbors(3/2r, 10)
209
+ # => [(1/1), (2/1), (4/3), (5/3), (7/5), (8/5), (10/7), (11/7), (13/9), (14/9)]
210
+ # @param number with neighbors
211
+ # @param range of harmonic series to search
212
+ #
213
+ def farey_neighbors(number, range = 10**(decimal_power(number.numerator)+2))
214
+ ratio = number.to_r
215
+ denominator = ratio.denominator
216
+
217
+ [].tap do |collection|
218
+ (1..range-1).each do |i|
219
+ lower, upper = plus_minus(ratio, Rational(1,i*denominator))
220
+ collection << lower if farey_neighbors?(ratio, lower)
221
+ collection << upper if farey_neighbors?(ratio, upper)
222
+ end
223
+ end
224
+ end
225
+
226
+ # @return [Boolean] whether two numbers are Farey neighbors
227
+ # @example
228
+ # FractionTree.farey_neighbors?(3/2r, 4/3r) => true
229
+ # FractionTree.farey_neighbors?(3/2r, 7/4r) => false
230
+ # @param num1 of comparison
231
+ # @param num2 of comparison
232
+ #
233
+ def farey_neighbors?(num1, num2)
234
+ (num1.numerator * num2.denominator - num1.denominator * num2.numerator).abs == 1
235
+ end
236
+
203
237
  private
204
238
  def computed_base_segment(number)
205
239
  floor = number.floor
@@ -215,18 +249,15 @@ class FractionTree
215
249
  _sequence(depth - 1, segment: [segment.first, mediant]) + [mediant] + _sequence(depth - 1, segment: [mediant, segment.last])
216
250
  end
217
251
 
218
- def farey_neighbors?(num1, num2)
219
- (num1.numerator * num2.denominator - num1.denominator * num2.numerator).abs == 1
252
+ def plus_minus(number, diff)
253
+ [number - diff, number + diff]
254
+ end
255
+
256
+ def decimal_power(number)
257
+ Math.log10(number.abs).floor
220
258
  end
221
259
  end
222
260
 
223
- # @attr_reader numerator [Integer]
224
- # The numerator of the node
225
- # @attr_reader denominator [Integer]
226
- # The denominator of the node
227
- # @attr_reader weight [Rational|Infinity]
228
- # The value of the node
229
- #
230
261
  class Node
231
262
  include Comparable
232
263
 
@@ -256,8 +287,16 @@ class FractionTree
256
287
  # Needed for intersection operations to work.
257
288
  # https://blog.mnishiguchi.com/ruby-intersection-of-object-arrays
258
289
  # https://shortrecipes.blogspot.com/2006/10/ruby-intersection-of-two-arrays-of.html
290
+ # Also, allows using with Set, which uses Hash as storage and equality of its elements is determined according to Object#eql? and Object#hash.
291
+ #
259
292
  def eql?(rhs)
260
- rhs.kind_of?(self.class) && weight == rhs.weight
293
+ rhs.instance_of?(self.class) && weight == rhs.weight
294
+ end
295
+
296
+ def hash
297
+ p, q = 17, 37
298
+ p = q * @id.hash
299
+ p = q * @name.hash
261
300
  end
262
301
 
263
302
  def +(rhs)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: fraction-tree
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.2
4
+ version: 1.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jose Hales-Garcia
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-12-22 00:00:00.000000000 Z
11
+ date: 2024-01-16 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: continued_fractions
@@ -66,6 +66,20 @@ dependencies:
66
66
  - - "~>"
67
67
  - !ruby/object:Gem::Version
68
68
  version: '0.9'
69
+ - !ruby/object:Gem::Dependency
70
+ name: rspec-benchmark
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: '0.6'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: '0.6'
69
83
  description: A collection of Stern-Brocot based models and methods
70
84
  email: jose@halesgarcia.com
71
85
  executables: []
@@ -93,7 +107,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
93
107
  - !ruby/object:Gem::Version
94
108
  version: '3.1'
95
109
  requirements: []
96
- rubygems_version: 3.5.1
110
+ rubygems_version: 3.5.3
97
111
  signing_key:
98
112
  specification_version: 4
99
113
  summary: Fraction tree