Class: Expression

Inherits:
Object
  • Object
show all
Defined in:
lib/chebyruby/expression.rb

Overview

This is a class for generic expressions. Whereas univariate functions are analogous to named functions this is more similar to a lambda. Additionally, this is more in the field of CAS instead of numerical analysis. Note: This is not at all stable or well tested and exists to try out but do not at all rely on this class.

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(left, op, right) ⇒ Expression

The constructor for the class Expression

Parameters:

  • left (Object)

    the left side of the expression

  • op (Operator)

    the binary operator

  • right (Object)

    the right side of the expression



21
22
23
24
25
# File 'lib/chebyruby/expression.rb', line 21

def initialize(left, op, right)
  @left = left
  @op = op
  @right = right
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(method, *args) ⇒ Object

The method missing method for expressions. Using some swanky tricks, a non-extant method on an expression is turned into a binary operator using a symbol and creates a new expression with the left expression being nested into a unit. Thus the expressions are by default left associative.

Parameters:

  • method (Object)

    the method that is missing

  • args (Object[])

    the args that are passed to the missing method

Returns:

  • a new expression



36
37
38
# File 'lib/chebyruby/expression.rb', line 36

def method_missing(method, *args)
  Expression.new(self, method, Variable.new(args[0]))
end

Instance Attribute Details

#leftObject

the left side of the expression (on a binary operator)

Returns:

  • (Object)

    the current value of left



13
14
15
# File 'lib/chebyruby/expression.rb', line 13

def left
  @left
end

#opOperator

the binary operator

Returns:

  • (Operator)

    the current value of op



13
14
15
# File 'lib/chebyruby/expression.rb', line 13

def op
  @op
end

#rightObject

the right side of the expression

Returns:

  • (Object)

    the current value of right



13
14
15
# File 'lib/chebyruby/expression.rb', line 13

def right
  @right
end

Instance Method Details

#nested?Boolean

This method returns a hash describing if the right and/or left sides of an expression are nested.

Returns:

  • (Boolean)

    a boolean hash with keys [:right, :left]



57
58
59
60
# File 'lib/chebyruby/expression.rb', line 57

def nested?
  {:right => (Expression === right),
   :left => (Expression === left)}
end

#to_funcObject

This turns the anonymous expression into a function

Returns:

  • a function of the expression.



81
82
83
84
85
86
# File 'lib/chebyruby/expression.rb', line 81

def to_func
  if a.vars.size == 1
    blk = ->(intvar) {eval(to_s.gsub(vars[0],'intvar'))}
    UnivariateFunction.new(&blk)
  end
end

#to_sObject

This method returns a string version of an expression.

Returns:

  • a string version of an expression



65
66
67
68
69
70
71
72
73
74
75
76
# File 'lib/chebyruby/expression.rb', line 65

def to_s
  if nested?[:left]
    s = "#{left.to_s} #{op}"
  else
    s = "#{left} #{op}"
  end
  case right
  when Variable then "#{s} #{right.x}".strip
  when Expression then "#{s} #{right.to_s}".strip
  else "#{s} #{right}".strip
  end
end

#varsObject

This method returns a flattened list of the variables within an expression. For example, the expression ((x + y) + z) + a will have a vars of [x, y, z, a]

Returns:

  • an array of the variables



46
47
48
49
50
51
# File 'lib/chebyruby/expression.rb', line 46

def vars
  a = []
  nested?[:left] ? a << left.vars : a << left.x
  nested?[:right] ? a << right.vars : a << right.x
  (a.flatten rescue a).select{|i| String === i}.uniq
end