Class: Unitwise::Unit

Inherits:
Object
  • Object
show all
Includes:
Compatible
Defined in:
lib/unitwise/unit.rb

Overview

A Unit is essentially a collection of Unitwise::Term. Terms can be combined through multiplication or division to create a unit. A unit does not have a magnitude, but it does have a scale.

Instance Method Summary collapse

Methods included from Compatible

#<=>, #compatible_with?, #composition, #composition_string, #dim, included

Constructor Details

#initialize(input) ⇒ Unit

Create a new unit. You can send an expression or a collection of terms collection of tems.

Parameters:

  • input (String, Unit, [Term])

    A string expression, a unit, or a



13
14
15
16
17
18
19
20
21
22
# File 'lib/unitwise/unit.rb', line 13

def initialize(input)
  case input
  when Compatible
    @expression = input.expression
  when String, Symbol
    @expression = input.to_s
  else
    @terms = input
  end
end

Instance Method Details

#*(other) ⇒ Unitwise::Unit

Multiply this unit by another unit, term, or number.

Parameters:

Returns:



110
111
112
113
# File 'lib/unitwise/unit.rb', line 110

def *(other)
  operate('*', other) ||
    fail(TypeError, "Can't multiply #{ self } by #{ other }.")
end

#**(other) ⇒ Unitwise::Unit

Raise this unit to a numeric power.

Parameters:

  • other (Numeric)

Returns:



129
130
131
132
133
134
135
# File 'lib/unitwise/unit.rb', line 129

def **(other)
  if other.is_a?(Numeric)
    self.class.new(terms.map { |t| t ** other })
  else
    fail TypeError, "Can't raise #{self} to #{other}."
  end
end

#/(other) ⇒ Unitwise::Unit

Divide this unit by another unit,term, or number.

Parameters:

Returns:



119
120
121
122
# File 'lib/unitwise/unit.rb', line 119

def /(other)
  operate('/', other) ||
    fail(TypeError, "Can't divide #{ self } by #{ other }.")
end

#aliasesArray

A collection of the possible string representations of this unit. Primarily used by Unitwise::Search.

Returns:

  • (Array)


150
151
152
153
154
# File 'lib/unitwise/unit.rb', line 150

def aliases
  [:names, :primary_code, :secondary_code, :symbol].map do |mode|
    to_s(mode)
  end.uniq
end

#atomsArray

The collection of atoms that compose this unit. Essentially delegated to terms.

Returns:

  • (Array)


56
57
58
# File 'lib/unitwise/unit.rb', line 56

def atoms
  terms.map(&:atom)
end

#depthInteger

A number representing this unit's distance from it's deepest terminal atom.

Returns:

  • (Integer)


72
73
74
# File 'lib/unitwise/unit.rb', line 72

def depth
  terms.map(&:depth).max + 1
end

#expression(mode = nil) ⇒ String

Build a string representation of this unit by it's terms. (:primary_code, :names, :secondary_code).

Parameters:

  • mode (Symbol) (defaults to: nil)

    The mode to use to stringify the atoms

Returns:

  • (String)


44
45
46
47
48
49
50
# File 'lib/unitwise/unit.rb', line 44

def expression(mode=nil)
  if @expression && (mode.nil? || mode == self.mode)
    @expression
  else
    Expression.compose(terms, mode || self.mode)
  end
end

#magnitude(scalar = scalar()) ⇒ Numeric

Get a magnitude for this unit based on a linear scale value. Should only be used by units with special atoms in it's hierarchy.

Parameters:

  • scalar (Numeric) (defaults to: scalar())

    A linear scalar value

Returns:

  • (Numeric)

    The equivalent magnitude on this scale



100
101
102
103
104
# File 'lib/unitwise/unit.rb', line 100

def magnitude(scalar = scalar())
  terms.reduce(1) do |prod, term|
    prod * term.magnitude(scalar)
  end
end

#modeSymbol

The default mode to use for inspecting and printing.

Returns:

  • (Symbol)


160
161
162
163
# File 'lib/unitwise/unit.rb', line 160

def mode
  terms
  @mode || :primary_code
end

#root_termsArray

A collection of the deepest terms, or essential composition of the unit.

Returns:

  • (Array)


80
81
82
# File 'lib/unitwise/unit.rb', line 80

def root_terms
  terms.map(&:root_terms).flatten
end

#scalar(magnitude = 1) ⇒ Numeric

Get a scalar value for this unit.

Parameters:

  • magnitude (Numeric) (defaults to: 1)

    An optional magnitude on this unit's scale.

Returns:

  • (Numeric)

    A scalar value on a linear scale



89
90
91
92
93
# File 'lib/unitwise/unit.rb', line 89

def scalar(magnitude = 1)
  terms.reduce(1) do |prod, term|
    prod * term.scalar(magnitude)
  end
end

#special?true, false

Is this unit special (meaning on a non-linear scale)?

Returns:

  • (true, false)


64
65
66
# File 'lib/unitwise/unit.rb', line 64

def special?
  terms.count == 1 && terms.all?(&:special?)
end

#termsArray

The collection of terms used by this unit.

Returns:

  • (Array)


27
28
29
30
31
32
33
34
35
36
37
# File 'lib/unitwise/unit.rb', line 27

def terms
  unless frozen?
    unless @terms
      decomposer = Expression.decompose(@expression)
      @mode  = decomposer.mode
      @terms = decomposer.terms
    end
    freeze
  end
  @terms
end

#to_s(mode = nil) ⇒ String

A string representation of this unit. (:primary_code, :names, :secondary_code)

Parameters:

  • mode (:symbol) (defaults to: nil)

    The mode used to represent the unit

Returns:

  • (String)


142
143
144
# File 'lib/unitwise/unit.rb', line 142

def to_s(mode = nil)
  expression(mode)
end