Class: SY::Composition
- Inherits:
-
Hash
- Object
- Hash
- SY::Composition
- Defined in:
- lib/sy/composition.rb
Overview
Composition of quantities.
Constant Summary collapse
- SR =
Simplification rules for quantity combinations.
SIMPLIFICATION_RULES = []
- QUANTITY_TABLE =
Cache for quantity construction.
Hash.new { |
Class Method Summary collapse
Instance Method Summary collapse
-
#*(number) ⇒ Object
Multiplication by a number.
-
#+(other) ⇒ Object
Merges two compositions.
-
#+@ ⇒ Object
Returns a new instance with same hash.
-
#-(other) ⇒ Object
Subtracts two compositions.
-
#-@ ⇒ Object
Negates hash exponents.
-
#/(number) ⇒ Object
Division by a number.
-
#atomic? ⇒ Boolean
Atomic compositions are singular compositions, whose quantity dimension is a base dimension.
-
#coerces?(other) ⇒ Boolean
Whether this composition coerces another compotision.
-
#dimension ⇒ Object
Dimension of a composition is the sum of its member quantities’ dimensions.
-
#expand ⇒ Object
Try to simplify the composition by decomposing its quantities.
-
#infer_measure ⇒ Object
Infers the measure of the composition’s quantity.
-
#irreducible? ⇒ Boolean
Whether it is possible to expand this.
-
#new_quantity(args = {}) ⇒ Object
Directly (without attempts to simplify) creates a new quantity from self.
-
#simple? ⇒ Boolean
Simple composition is one that is either empty or singular.
-
#simplify ⇒ Object
Simplifies a quantity hash by applying simplification rules.
-
#singular? ⇒ Boolean
Singular compositions consist of only one quantity.
-
#to_quantity(args = {}) ⇒ Object
Returns the quantity appropriate to this composition.
Class Method Details
.empty ⇒ Object
65 66 67 |
# File 'lib/sy/composition.rb', line 65 def empty self[] end |
.singular(quantity) ⇒ Object
61 62 63 |
# File 'lib/sy/composition.rb', line 61 def singular quantity self[ SY.Quantity( quantity ) => 1 ] end |
Instance Method Details
#*(number) ⇒ Object
Multiplication by a number.
168 169 170 |
# File 'lib/sy/composition.rb', line 168 def * number self.class[ self.with_values do |v| v * number end ] end |
#+(other) ⇒ Object
Merges two compositions.
156 157 158 |
# File 'lib/sy/composition.rb', line 156 def + other self.class[ self.merge( other ) { |_, v1, v2| v1 + v2 } ] end |
#+@ ⇒ Object
Returns a new instance with same hash.
144 145 146 |
# File 'lib/sy/composition.rb', line 144 def +@ self.class[ self ] end |
#-(other) ⇒ Object
Subtracts two compositions.
162 163 164 |
# File 'lib/sy/composition.rb', line 162 def - other self + -other end |
#-@ ⇒ Object
Negates hash exponents.
150 151 152 |
# File 'lib/sy/composition.rb', line 150 def -@ self.class[ self.with_values do |v| -v end ] end |
#/(number) ⇒ Object
Division by a number.
174 175 176 177 178 179 180 |
# File 'lib/sy/composition.rb', line 174 def / number self.class[ self.with_values do |val| raise TErr, "Compositions with rational exponents " + "not implemented!" if val % number != 0 val / number end ] end |
#atomic? ⇒ Boolean
Atomic compositions are singular compositions, whose quantity dimension is a base dimension.
109 110 111 112 113 |
# File 'lib/sy/composition.rb', line 109 def atomic? puts "composition is #{self}" if SY::DEBUG puts "first[0].dimension is #{first[0].dimension}" if SY::DEBUG singular? && first[0].dimension.base? end |
#coerces?(other) ⇒ Boolean
Whether this composition coerces another compotision.
117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 |
# File 'lib/sy/composition.rb', line 117 def coerces? other # TODO: Think about caching. One way, ie. no way back, once something # coerces something else, so only false results would have to be re-checked, # and that only at most once each time after coerces / coerced_by method is # tampered. if singular? then other.singular? && self.first[0].coerces?( other.first[0] ) else # simplify the compositions a bit rslt = [].tap do |ary| find { |qnt, e| other.find { |qnt2, e2| ( ( e > 0 && e2 > 0 || e < 0 && e2 < 0 ) && qnt.coerces?( qnt2 ) ) .tap { |rslt| [] << qnt << qnt2 << ( e > 0 ? -1 : 1 ) if rslt } } } end # and ask recursively if rslt.empty? then return false else q, q2, e = rslt ( self + q.composition * e ).coerces? ( other + q2.composition * e ) end end end |
#dimension ⇒ Object
Dimension of a composition is the sum of its member quantities’ dimensions.
208 209 210 |
# File 'lib/sy/composition.rb', line 208 def dimension map { |qnt, exp| qnt.dimension * exp }.reduce SY::Dimension.zero, :+ end |
#expand ⇒ Object
Try to simplify the composition by decomposing its quantities.
243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 |
# File 'lib/sy/composition.rb', line 243 def return self if irreducible? puts "#expand: #{self} not irreducible" if SY::DEBUG self.class[ reduce( self.class.empty ) { |c |
#infer_measure ⇒ Object
Infers the measure of the composition’s quantity. (‘Measure’ means measure of the pertinent standard quantity.)
215 216 217 218 219 220 221 222 223 224 225 226 227 228 |
# File 'lib/sy/composition.rb', line 215 def infer_measure puts "#infer_measure; hash is #{self}" if SY::DEBUG map do |qnt, exp| puts "#infer_measure: doing quantity #{qnt} with exponent #{exp}!" if SY::DEBUG if qnt.standardish? then puts "#{qnt} standardish" if SY::DEBUG SY::Measure.identity else puts "#{qnt} not standardish" if SY::DEBUG puts "its measure is #{qnt.measure}, class #{qnt.measure.class}" if SY::DEBUG qnt.measure( of: qnt.standard ) ** exp end end.reduce( SY::Measure.identity, :* ) end |
#irreducible? ⇒ Boolean
Whether it is possible to expand this
237 238 239 |
# File 'lib/sy/composition.rb', line 237 def irreducible? all? { |qnt, exp| qnt.irreducible? } end |
#new_quantity(args = {}) ⇒ Object
Directly (without attempts to simplify) creates a new quantity from self. If self is empty or singular, SY::Amount, resp. the singular quantity in question is returned.
202 203 204 |
# File 'lib/sy/composition.rb', line 202 def new_quantity args={} SY::Quantity.new args.merge( composition: self ) end |
#simple? ⇒ Boolean
Simple composition is one that is either empty or singular.
232 233 234 |
# File 'lib/sy/composition.rb', line 232 def simple? empty? or singular? end |
#simplify ⇒ Object
Simplifies a quantity hash by applying simplification rules.
184 185 186 187 188 189 |
# File 'lib/sy/composition.rb', line 184 def simplify |
#singular? ⇒ Boolean
Singular compositions consist of only one quantity.
102 103 104 |
# File 'lib/sy/composition.rb', line 102 def singular? size == 1 && first[1] == 1 end |
#to_quantity(args = {}) ⇒ Object
Returns the quantity appropriate to this composition.
193 194 195 196 |
# File 'lib/sy/composition.rb', line 193 def to_quantity args={} # All the work is delegated to the quantity table: QUANTITY_TABLE[ args.merge( self ) ] end |