Class: Quanty::Fact

Inherits:
Hash
  • Object
show all
Defined in:
lib/oddb/util/quanty/fact.rb

Constant Summary collapse

Self =
self
Parser =
Parse.new

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(key = nil, si = false) ⇒ Fact

SI units: Fact.new(“m”,true) => “m”=>1 Derivative units: Fact.new(“km”) => 1000*“m”=>1



20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
# File 'lib/oddb/util/quanty/fact.rb', line 20

def initialize(key=nil,si=false)
  self.default = 0.0
  @factor = 1.0
  case key
  when Numeric
	@factor = key
  when String
	if si
	  store(key, 1.0)
	else
	  decomp(key)
	end
  when Self
	replace(key)
  end
end

Instance Attribute Details

#factorObject

Returns the value of attribute factor.



16
17
18
# File 'lib/oddb/util/quanty/fact.rb', line 16

def factor
  @factor
end

Class Method Details

.mkdump(filename) ⇒ Object



189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
# File 'lib/oddb/util/quanty/fact.rb', line 189

def mkdump(filename)
	Prefix.clear
	List.clear
  SI.clear
	#s = open("units.succ","w")
	#f = open("units.fail","w")
	open("units.dat","r").readlines.each do |str|
	  if /^([µA-Za-z_0-9%$"'-]+)\s+([^#]+)/ =~ str #"
	    name,repr = $1,$2.strip
	    # conversion due to the different rule from GNU units:
	    #   A / B C => A / (B C)
	    if /\// =~ repr #/
 pre,suf = $`,$'.strip #`
 if /\s/ =~ suf
		repr = pre + ' / (' + suf + ')'
 end
	    end
	    if repr=="!" # SI
 List[name] = Fact.new(name,true).freeze
        SI << name
	    elsif /-$/  =~ name
 Prefix[name[0..-2]] = Prefix[repr] || (List[repr] || repr).to_f
	    else
 #p [name,repr]
 List[name] = Fact.new(repr).freeze
	    end
	    #s.print str
	    #rescue
	    #f.print str
	  end
	end
	#Prefix.each{|key,val| p [key,val]}
	#List.each{|key,val| p [key,val]}
	Marshal.dump( [Prefix, List, SI], open(filename,"w") )
end

Instance Method Details

#*(other) ⇒ Object



97
98
99
# File 'lib/oddb/util/quanty/fact.rb', line 97

def * (other)
  dup.mul!(other)
end

#**(other) ⇒ Object



120
121
122
# File 'lib/oddb/util/quanty/fact.rb', line 120

def ** (other)
  dup.pow!(other)
end

#/(other) ⇒ Object



109
110
111
# File 'lib/oddb/util/quanty/fact.rb', line 109

def / (other)
  dup.div!(other)
end

#==(other) ⇒ Object



166
167
168
169
170
171
172
# File 'lib/oddb/util/quanty/fact.rb', line 166

def ==(other)
  if other.kind_of?(Numeric)
	null? && @factor==other
  else
	__equal__(other) && @factor==other.factor
  end
end

#===(other) ⇒ Object

check only dimension



175
176
177
178
179
180
181
# File 'lib/oddb/util/quanty/fact.rb', line 175

def ===(other)
  if other.kind_of?(Numeric)
	null?
  else
	__equal__(other)
  end
end

#[]=(key, val) ⇒ Object



37
38
39
40
41
42
43
# File 'lib/oddb/util/quanty/fact.rb', line 37

def []=(key,val)
  if val == 0
	delete(key)
  else
	super(key,val)
  end
end

#__equal__Object



164
# File 'lib/oddb/util/quanty/fact.rb', line 164

alias __equal__ :==

#decomp(a) ⇒ Object



67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
# File 'lib/oddb/util/quanty/fact.rb', line 67

def decomp(a)
  if /^([µA-Za-z_]+([A-Za-z_0-9-]+[A-Za-z_])?)$|^[$%'"]'?$/o =~ a
  #if /^[A-Za-z_0-9$%-]+$/o =~ a
	unit = List[a] || find_prefix(a,0) ||
	  if a.size>3 && /chs$/o !~ a && /(.*[a-rt-y])s$/o =~ a
 b = $1
 List[b] || find_prefix(b,2) ||
   if a.size>4 && /(.*s|.*z|.*ch)es$/o =~ a
		b = $1
		List[b] || find_prefix(b,2)
   end
	  end
  else
	unit = Parser.parse(a)
  end
  unless unit
	raise "`%s': unknown unit"%a 
  end
  @factor *= factor if factor
  mul!(unit)
end

#div!(other) ⇒ Object



101
102
103
104
105
106
107
# File 'lib/oddb/util/quanty/fact.rb', line 101

def div!(other)
  raise unless other.kind_of?(Fact)
  other.each{ |key,val| self[key] -= val }
  delete_if{ |key,val| val == 0 }
  @factor /= other.factor
  self
end

#dupObject



50
51
52
# File 'lib/oddb/util/quanty/fact.rb', line 50

def dup
  Fact.new(self)
end

#fac!(other) ⇒ Object



124
125
126
127
128
# File 'lib/oddb/util/quanty/fact.rb', line 124

def fac!(other)
  raise unless other.kind_of?(Numeric)
  @factor *= other
  self
end

#find_prefix(a, n) ⇒ Object



57
58
59
60
61
62
63
64
65
# File 'lib/oddb/util/quanty/fact.rb', line 57

def find_prefix(a,n)
  Prefix.each{ |key,factor|
	if /^#{key}-?/ =~ a && (unit = List[b=$']) && b.size>n
	  #p [a,b,factor]
	  return Fact.new(b).fac!(factor)
	end
  }
  nil
end

#inspectObject



130
131
132
# File 'lib/oddb/util/quanty/fact.rb', line 130

def inspect
  @factor.to_s+"*"+super
end

#mul!(other) ⇒ Object



89
90
91
92
93
94
95
# File 'lib/oddb/util/quanty/fact.rb', line 89

def mul!(other)
  raise unless other.kind_of?(Fact)
  other.each{ |key,val| self[key] += val }
  delete_if{ |key,val| val == 0 }
  @factor *= other.factor
  self
end

#null?Boolean

Returns:

  • (Boolean)


159
160
161
162
# File 'lib/oddb/util/quanty/fact.rb', line 159

def null?
  each_value{ |val| return false if val != 0 }
  true
end

#pow!(other) ⇒ Object



113
114
115
116
117
118
# File 'lib/oddb/util/quanty/fact.rb', line 113

def pow!(other)
  raise unless other.kind_of?(Numeric)
  each{ |key,val| self[key] = other*val }
  @factor **= other
  self
end

#replace(other) ⇒ Object



45
46
47
48
# File 'lib/oddb/util/quanty/fact.rb', line 45

def replace(other)
  @factor = other.factor
  super(other)
end

#to_fObject



183
184
185
186
# File 'lib/oddb/util/quanty/fact.rb', line 183

def to_f
  raise inspect + ": not null unit" unless null?
  @factor
end

#to_quantyObject



153
154
155
156
157
# File 'lib/oddb/util/quanty/fact.rb', line 153

def to_quanty
  f = dup
  f.factor = 1.0
  Quanty(@factor, unit(), f)
end

#to_sObject



149
150
151
# File 'lib/oddb/util/quanty/fact.rb', line 149

def to_s
  @factor.to_s+" "+unit()
end

#unitObject



134
135
136
137
138
139
140
141
142
143
144
145
146
147
# File 'lib/oddb/util/quanty/fact.rb', line 134

def unit
  a = []
  SI.each do |k|
    v = self[k]
    if v && v!=0
      if v != 1
        v  = v.to_i if v%1 == 0
        k += v.to_s
      end
      a.push(k)
	end
  end
  a.join(" ")
end