ruby Integration¶
This example demonstrates how to use fluids from ruby.
Source Code¶
1require 'pycall'
2
3# Import fluids
4Fluids = PyCall.import_module('fluids')
5
6def test_fluids
7 begin
8 # 1. Test basic module import
9 puts "✓ Successfully imported fluids"
10 puts "✓ Fluids version: #{Fluids.__version__}"
11
12 # 2. Test basic Reynolds number calculation
13 re = Fluids.Reynolds(V: 2.5, D: 0.1, rho: 1000, mu: 0.001)
14 puts "✓ Reynolds number calculation successful: #{re}"
15 raise unless re > 0
16
17 # 3. Test friction factor calculation
18 fd = Fluids.friction_factor(Re: 1e5, eD: 0.0001)
19 puts "✓ Friction factor calculation successful: #{fd}"
20 raise unless (0 < fd && fd < 1)
21
22 puts "\nAll basic tests completed successfully!"
23 rescue => e
24 puts "Error occurred: #{e}"
25 raise
26 end
27end
28
29def test_atmosphere
30 begin
31 # Test ATMOSPHERE_1976 class
32 atm = Fluids.ATMOSPHERE_1976.new(Z: 5000)
33
34 puts "\nTesting atmosphere at 5000m elevation:"
35 puts "✓ Temperature: #{PyCall.getattr(atm, :T).round(4)}"
36 puts "✓ Pressure: #{PyCall.getattr(atm, :P).round(4)}"
37 puts "✓ Density: #{PyCall.getattr(atm, :rho).round(6)}"
38
39 # Test derived properties
40 puts "✓ Gravity: #{PyCall.getattr(atm, :g).round(6)}"
41 puts format("✓ Viscosity: %.6e", PyCall.getattr(atm, :mu))
42 puts "✓ Thermal conductivity: #{PyCall.getattr(atm, :k).round(6)}"
43 puts "✓ Sonic velocity: #{PyCall.getattr(atm, :v_sonic).round(4)}"
44
45 # Test static methods
46 g_high = Fluids.ATMOSPHERE_1976.gravity(Z: 1E5)
47 puts "✓ High altitude gravity: #{g_high.round(6)}"
48
49 v_sonic = Fluids.ATMOSPHERE_1976.sonic_velocity(T: 300)
50 puts "✓ Sonic velocity at 300K: #{v_sonic.round(4)}"
51
52 mu_400 = Fluids.ATMOSPHERE_1976.viscosity(T: 400)
53 puts format("✓ Viscosity at 400K: %.6e", mu_400)
54
55 k_400 = Fluids.ATMOSPHERE_1976.thermal_conductivity(T: 400)
56 puts "✓ Thermal conductivity at 400K: #{k_400.round(6)}"
57 rescue => e
58 puts "Error in atmosphere tests: #{e}"
59 raise
60 end
61end
62
63def test_tank
64 begin
65 # Test basic tank creation
66 t1 = Fluids.TANK.new(V: 10, L_over_D: 0.7, sideB: "conical", horizontal: false)
67 puts "\nTesting tank calculations:"
68 puts "✓ Tank length: #{t1.L.round(6)}"
69 puts "✓ Tank diameter: #{t1.D.round(6)}"
70
71 # Test ellipsoidal tank
72 tank_ellip = Fluids.TANK.new(D: 10, V: 500, horizontal: false,
73 sideA: "ellipsoidal", sideB: "ellipsoidal",
74 sideA_a: 1, sideB_a: 1)
75 puts "✓ Ellipsoidal tank L: #{tank_ellip.L.round(6)}"
76
77 # Test torispherical tank
78 din = Fluids.TANK.new(L: 3, D: 5, horizontal: false,
79 sideA: "torispherical", sideB: "torispherical",
80 sideA_f: 1, sideA_k: 0.1, sideB_f: 1, sideB_k: 0.1)
81
82 puts "✓ Tank representation: #{din}"
83 puts "✓ Tank max height: #{din.h_max.round(6)}"
84 puts "✓ Height at V=40: #{din.h_from_V(40).round(6)}"
85 puts "✓ Volume at h=4.1: #{din.V_from_h(4.1).round(5)}"
86 puts "✓ Surface area at h=2.1: #{din.SA_from_h(2.1).round(5)}"
87 rescue => e
88 puts "Error in tank tests: #{e}"
89 raise
90 end
91end
92
93def test_reynolds
94 begin
95 puts "\nTesting Reynolds number calculations:"
96
97 # Test with density and viscosity
98 re1 = Fluids.Reynolds(V: 2.5, D: 0.25, rho: 1.1613, mu: 1.9E-5)
99 puts "✓ Re (with rho, mu): #{re1.round(4)}"
100 raise unless (re1 - 38200.6579).abs < 0.1
101
102 # Test with kinematic viscosity
103 re2 = Fluids.Reynolds(V: 2.5, D: 0.25, nu: 1.636e-05)
104 puts "✓ Re (with nu): #{re2.round(4)}"
105 raise unless (re2 - 38202.934).abs < 0.1
106 rescue => e
107 puts "Error in Reynolds tests: #{e}"
108 raise
109 end
110end
111
112def test_psd
113 begin
114 puts "\nTesting particle size distribution functionality:"
115
116 # Create a discrete PSD
117 ds = [240, 360, 450, 562.5, 703, 878, 1097, 1371, 1713, 2141, 2676, 3345, 4181, 5226, 6532]
118 numbers = [65, 119, 232, 410, 629, 849, 990, 981, 825, 579, 297, 111, 21, 1]
119
120 psd = Fluids.particle_size_distribution.ParticleSizeDistribution.new(
121 ds: ds,
122 fractions: numbers,
123 order: 0
124 )
125 puts "✓ Created discrete PSD"
126
127 # Test mean sizes
128 d21 = psd.mean_size(2, 1)
129 puts "✓ Size-weighted mean diameter: #{d21.round(4)}"
130 raise unless (d21 - 1857.788).abs < 0.1
131
132 d10 = psd.mean_size(1, 0)
133 puts "✓ Arithmetic mean diameter: #{d10.round(4)}"
134 raise unless (d10 - 1459.372).abs < 0.1
135
136 # Test percentile calculations
137 d10_percentile = psd.dn(0.1)
138 d90_percentile = psd.dn(0.9)
139 puts "✓ D10: #{d10_percentile.round(4)}"
140 puts "✓ D90: #{d90_percentile.round(4)}"
141
142 # Test probability functions
143 pdf_val = psd.pdf(1000)
144 cdf_val = psd.cdf(5000)
145 puts "✓ PDF at 1000: %.4e" % pdf_val
146 puts "✓ CDF at 5000: #{cdf_val.round(6)}"
147
148 # Test lognormal distribution
149 psd_log = Fluids.particle_size_distribution.PSDLognormal.new(s: 0.5, d_characteristic: 5E-6)
150 puts "✓ Created lognormal PSD"
151
152 vssa = psd_log.vssa
153 puts "✓ Volume specific surface area: #{vssa.round(2)}"
154
155 span = psd_log.dn(0.9) - psd_log.dn(0.1)
156 puts "✓ Span: %.4e" % span
157
158 ratio_7525 = psd_log.dn(0.75)/psd_log.dn(0.25)
159 puts "✓ D75/D25 ratio: #{ratio_7525.round(6)}"
160 rescue => e
161 puts "Error in PSD tests: #{e}"
162 raise
163 end
164end
165
166def benchmark_fluids
167 puts "\nRunning benchmarks:"
168
169 # Benchmark friction factor calculation
170 puts "\nBenchmarking friction_factor:"
171 t1 = Time.now
172 1_000_000.times do
173 Fluids.friction_factor(Re: 1e5, eD: 0.0001)
174 end
175 elapsed = Time.now - t1
176 puts "Time for 1e6 friction_factor calls: #{elapsed.round(6)} seconds"
177 puts "Average time per call: #{(elapsed/1_000_000).round(6)} seconds"
178
179 # Benchmark tank creation
180 puts "\nBenchmarking TANK creation:"
181 t2 = Time.now
182 1000.times do
183 Fluids.TANK.new(L: 3, D: 5, horizontal: false,
184 sideA: "torispherical", sideB: "torispherical",
185 sideA_f: 1, sideA_k: 0.1, sideB_f: 1, sideB_k: 0.1)
186 end
187 tank_elapsed = Time.now - t2
188 puts "Average time per creation: #{(tank_elapsed/1000).round(6)} seconds"
189end
190
191# Run all tests
192puts "Running fluids tests from Ruby..."
193test_fluids
194test_atmosphere
195test_tank
196test_reynolds
197test_psd
198benchmark_fluids
199puts "\nAll tests completed!"
Requirements¶
Python with fluids installed
Usage Notes¶
The example demonstrates basic integration with fluids
4 microsecond friction factor, 35 microsecond tank creation observed by author