Module: Polynomials::Analyzable
- Included in:
- Polynomial
- Defined in:
- lib/polynomials/analyzable.rb
Constant Summary collapse
- AfterExtremaCurvatureMapping =
{ maximum: :right, minimum: :left }
- MinimumOrMaximum =
{[1.0,-1.0] => :maximum,[-1.0,1.0] => :minimum}
Instance Method Summary collapse
- #curvature_behaviour ⇒ Object
- #inflection_points ⇒ Object
- #local_extrema ⇒ Object
- #strives_for ⇒ Object
Instance Method Details
#curvature_behaviour ⇒ Object
41 42 43 44 45 46 47 48 49 50 51 |
# File 'lib/polynomials/analyzable.rb', line 41 def curvature_behaviour hash = Hash.new {|h,k|h[k]=[]} dd = self.derivative.derivative strives_for = derivative.strives_for return nil if !strives_for delimiter = [strives_for[0]] | derivative.local_extrema.to_a | [strives_for[1]] delimiter.sort.each_cons(2).group_by do |b,_| AfterExtremaCurvatureMapping[b.kind_of_extremum] end.tap { |h| h.values.each { |a| a.each { |r| r.map!(&:x) }}} end |
#inflection_points ⇒ Object
16 17 18 |
# File 'lib/polynomials/analyzable.rb', line 16 def inflection_points self.derivative.local_extrema.map { |p| InflectionPoint.new(p.x,self.calculate(p.x)) }.to_set end |
#local_extrema ⇒ Object
20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
# File 'lib/polynomials/analyzable.rb', line 20 def local_extrema derivative = self.derivative possible_extrema = derivative.roots.sort.map(&:x) return Set[] if possible_extrema.empty? samples = possible_extrema.sort.each_cons(2).map do |before,after| (before + after)/2 end samples.unshift possible_extrema.first - 1 samples.push possible_extrema.last + 1 possible_extrema.zip(samples.each_cons(2)).inject(Set[]) do |set,(pe,sample)| directions = sample.map { |x| derivative.(x).sign } kind_of_extremum = MinimumOrMaximum[directions] next set unless kind_of_extremum set << Extremum.new(pe,self.calculate(pe), kind_of_extremum) end end |
#strives_for ⇒ Object
6 7 8 9 10 11 12 13 14 |
# File 'lib/polynomials/analyzable.rb', line 6 def strives_for points = self.roots.map(&:x) | self.local_extrema.map(&:x) return nil if points.empty? points.minmax.zip([-1,1]) .map do |point,direction| sign = self.(point + direction).sign Extremum.new(Infinity * direction, sign * Infinity, sign < 0 ? :minimum : :maximum) end end |