# -*- coding: utf-8 -*-
'''
Tools to calculate water system
design aspects
'''
from __future__ import print_function, division
from math import pi, acos, sqrt, ceil, exp
from Water import Imperial_properties as WATER
[docs]def coeffs(num_ERUs):
'''C and F coefficients from the `2019 DOH Water System Design Manual Table 3-1 <https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220#page=51>`__
:param num_ERUs: number of Equivalent Residential Units
:type num_ERUs: int
:return: C and F Coefficients
:rtype: tuple (C, F)
:Example:
>>> from Water import tools
>>> ERUs = 1500A = \\pi d^2 / 4
>>> C, F = tools.coeffs(ERUs)
'''
if num_ERUs < 51:
return 3.0, 0
elif num_ERUs > 50 and num_ERUs < 101:
return 2.5, 25
elif num_ERUs > 100 and num_ERUs < 251:
return 2.0, 75
elif num_ERUs > 250 and num_ERUs < 501:
return 1.8, 125
elif num_ERUs > 500:
return 1.6, 225
else:
raise Exception("Number of ERU's must be a positive integer")
[docs]def PHD(MDD, num_ERUs):
'''Peak Hour Demand Calculation from the `2019 DOH Water System Design Manual Table 3-1 <https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220#page=51>`__
.. math::
PHD &= \\frac{ERU_{MDD}}{1440}(C N + F) + 18
\\text{where:}
PHD &= \\text{Peak Hourly Demand, total system (gpm)}
C &= \\text{Coefficent Associated with Ranges of ERUs}
N &= \\text{Number of ERUs based on MDD}
F &= \\text{Factor Associated with Ranges of ERUs}
ERU_{MDD} &= \\text{Maximum Day Demand (gpd/ERU)}
C and F coefficients are automatically calculated within PHD equation
:param MDD: Maximum Day Demand (gpd/ERU)
:type MDD: int
:param num_ERUs: Number of ERUs based on MDD
:return: Peak Hour Demand (gpm)
:rtype: int/float
'''
C, F = coeffs(num_ERUs)
phd = (MDD/1440)*(C*num_ERUs + F) + 18
return phd
[docs]def equalizing_storage(PHD, Qs):
'''Equalizing Storage calculation from the `2019 DOH Water System Design Manual Equation 7-1 <https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220#page=190>`__
.. math::
ES &= 150(PHD - Q_s)
\\text{where:}
ES &= \\text{Equalizing Storage in gallons}
:param PHD: Peak Hour Demand in gallons per minute (gpm)
:type PHD: int/float
:param Qs: total source supply (gpm)
:type Qs: int/float
:return: Equalizing Storage (gal)
:rtype: int/float
'''
return (PHD-Qs)*150
[docs]def standby_storage(N,SBi, Td=1):
'''Standby Storage calculation from the `2019 DOH Water System Design Manual Equation 7-2 <https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220#page=191>`__
.. math::
SB &= (N)(SB_i)(T_d)
\\text{where:}
SB &= \\text{Total Standby Storage component in gallons}
:param N: number of Equivalent Residential Units (ERUs) based on MDD
:type N: int
:param SBi: locally adopted unit SB volume in gallons per day per ERU (gpd/ERU)
:type SBi: int
:param Td: Number of days selected to meet water system-determined standard of reliability, *default 1*
:type Td: int
:return: Total Standby Storage (gal)
:rtype: int
'''
[docs]def calc_hp(flow_rate, head, pump_eff=0.6, motor_eff=0.9):
'''Horsepower calculation for pumping water
.. math::
hp_{water}&=(Q)(TDH)\\bigg{(}\\frac{1\ psi}{2.308\ ft}\\bigg{)}\\bigg{(}\\frac{1\ hp}{1714 (psi\ gpm)}\\bigg{)}
hp_{break}&=\\frac{hp_{water}}{\eta_{pump}}
hp_{input}&=\\frac{hp_{break}}{\eta_{motor}}
\\text{where:}\\quad \\eta_{pump} &= \\text{pump efficiency}, \\quad \\eta_{motor} = \\text{motor efficiency}
:param flow_rate: pump flow rate in gallons per minute (gpm)
:type flow_rate: int/float
:param head: pump head in feet (ft)
:type head: int/float
:param pump_eff: pump efficiency, *default 0.6*
:type pump_eff: float
:param motor_eff: motor efficiency, *default 0.9*
:type motor_eff: float
:return: (water hp, break hp, input hp)
:rtype: tuple
:Example:
.. code-block:: python
from Water import tools
# pumping parameters
flow = 1000 # gpm
head = 500 # ft of water
water_hp, break_hp, input_hp = tools.calc_hp(flow, head)
print(water_hp, break_hp, input_hp)
>>> 126.26262626262626 210.43771043771042 233.81967826412267
'''
water_hp = (flow_rate*head)/3960
break_hp = water_hp/pump_eff
input_hp = break_hp/motor_eff
return (water_hp, break_hp, input_hp)
[docs]def velocity(flow, pipe_diam):
'''calculate velocity through a pipe
.. math::
v = \\frac{Q}{A}
:param flow: flow (gpm)
:type flow: int/float
:param pipe_diam: pipe diameter (inches)
:type pipe_diam: float
:return: velocity (fps)
'''
Q = gpm2cuftps(flow)
d = pipe_diam/12
V = (4*Q)/(pi*d**2)
return V
[docs]def flow(velocity, pipe_diam):
'''Calculate volumetric flowrate through a pipe
.. math::
Q = v A
:param velocity: velocity (fps)
:type velocity: int/float
:param pipe_diam: pipe diameter (inches)
:type pipe_diam: int/float
:return: flow through a pipe (gpm)
:rtype: float
'''
d = pipe_diam/12
A = pi/4 * d**2
Q= cuftps2gpm(velocity * A)
return Q
[docs]def gpm2cuftps(gpm):
''' Convert gallons per minute (gpm) to cubic feet per second (cuft/s)
:param gpm: gallons per minute (gpm)
:type gpm: int/float
:return: cubic feet per second (cuft/s)
:rtype: float
'''
return gpm * 0.00222802
[docs]def cuftps2gpm(cuftps):
''' Convert cubic feet per second (cuft/s) to gallons per minute (gpm)
:param cuftps: cubic feet per second (cuft/s)
:type cuftps: int/float
:return: gallons per minute (gpm)
:rtype: float
'''
return cuftps * 448.831169
[docs]def pipeDiameter(flow, velocity):
'''Returns pipe diameter, given flow and velocity
.. math::
d = \\sqrt{\\frac{4 Q}{\\pi v}}
:param flow: flow in gallons per minute (gpm)
:type flow: int/float
:param velocity: velocity in feet per second (FPS)
:type velocity: int/float
:return: pipe diameter in inches
:rtype: float
'''
pipe_diam = sqrt(4*gpm2cuftps(flow)/(velocity*pi))
pipe_diam = pipe_diam * 12
return pipe_diam
[docs]def reynolds(pipe_diam, flow=None, vel=None, viscosity=WATER.kinematic_viscosity):
'''Reynolds Number Calculation
.. math::
Re = \\frac{\\mu D_h}{\\nu}
:param pipe_diam: pipe diameter (inches)
:type pipe_diam: int/float
:param flow: flow (gpm), *default None*
:type flow: int/float
:param vel: velocity (fps), *default None*
:type vel: int/float
:param viscosity: kinematic viscosity of water (ft^2/s) *default 1.407E-5 ft^2/s*
:return: Reynolds Number
:rtype: int
'''
d = pipe_diam/12
if flow:
v = velocity(flow, pipe_diam)
re = d * v / viscocity
elif vel:
re = d * vel / viscocity
else:
raise Exception('Must enter flow or velocity')
return re
[docs]def volume_cyl(diameter, height):
''' calculate the volume of a cylinder
:param diameter: diameter of cylinder
:type diameter: int/float
:param height: height of cylinder
:type height: int/float
:return: volume of a cylinder in consistent units
:rtype: float
'''
return (pi*diameter**2 / 4)*height
[docs]def volume_box(length, width, height):
''' calculate the volume of a box
:param length: length of box
:type length: int/float
:param width: width of box
:type width: int/float
:param height: height of box
:type height: int/float
:return: volume of a box in consistent units
:rtype: float
'''
return length*width*height
[docs]def cuft2gal(cubic_feet):
''' cubic feet to gallon conversion
:param cubic_feet: cubic feet
:type cubic_feet: int/float
:return: gallons
:rtype: float
'''
return cubic_feet*7.4805
[docs]def gal2cuft(gallons):
''' gallon to cubic feet conversion
:param gallons: gallons
:type gallons: int/float
:return: cubic feet
:rtype: float
'''
return gallons/7.4805
[docs]def gal2acft(gallons):
'''gallons to acre-feet conversion
:param gallons: gallons
:type gallons: int/float
:return: acre feet
:rtype: float
'''
return gallons/325851
[docs]def acft2gal(acft):
'''acre-feet to gallons conversion
:param acft: acre feet
:type acft: int/float
:return: gallons
:rtype: float
'''
return acft * 325851
[docs]def cuin2gal(cubic_inches):
'''cubic inches to gallons conversion
:param cubic_inches: cubic inches
:type cubic_inches: int/float
:return: gallons
:rtype: float
'''
return cubic_inches/231
[docs]def gal2cuin(gallons):
'''gallon to cubic inch conversion
:param gallons: gallons
:type gallons: int/float
:return: cubic inches
:rtype: float
'''
return gallons * 231
[docs]def minor_loss(velocity, k_val ):
''' Uses `Minor Loss Equation`_ to calculate minor head loss through fittings in fittings_list.
.. _Minor Loss Equation: https://en.wikipedia.org/wiki/Minor_losses_in_pipe_flow#Minor_Losses
.. math:: h_{minor} = K_L\\cdot \\frac{v^2}{2g}
:param velocity: velocity (fps)
:param k_val: K value
:type velocity: int/float
:type velocity: int/float
:return: minor head loss (ft)
:rtype: float
'''
return k_val * velocity**2/(2*WATER.g)
[docs]def kinetic_loss(velocity):
'''calculate the kinetic loss term in the bernoulli equation
..math:: \\frac{v^2}{2g}
'''
return velocity**2/(2*WATER.g)
[docs]def ft2psi(ft_of_head):
'''feet of head to pounds per square inch (psi) conversion
:param ft_of_head: feet of head
:type ft_of_head: int/float
:return: psi
:rtype: float
'''
return ft_of_head * 0.433333333
[docs]def psi2ft(psi):
''' return psi to feet of head
:param psi: pounds per square feet (psi)
:type psi: int/float
:return: feet of head
:rtype: float
'''
return psi * 2.3077
[docs]def hpn_size(cut_out, cut_in, num_cycles, max_flow, tank_diam, shape='horiztonal'):
''' Conventional hydro-pneumatic tank sizing calculation from the `2019 DOH Water System Design Manual Equations 9-2 and 9-3 <https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220#page=230>`__
:param cut_out: P :sub:`1` nominal pump-off pressure (psi)
:param cut_in: P :sub:`2` nominal pump-on pressure (psi)
:param num_cycles: max number of cycles/hour/pump (Nc)
:param max_flow: estimated max flow from 1 pump (Qp)
:param tank_diam: diameter of tank (inches)
:param shape: tank shape (must be 'horizontal' or 'vertical')
:type cut_out: int/float
:type cut_in: int/float
:type num_cycles: int
:type max_flow: int/float
:type tank_diam: int/float
:type shape: string
:return: recommended volume for hydro-pnuematic tank
:rtype: float
'''
assert (shape == 'horizontal' or shape == 'vertical'), "shape must be horizontal or vertical"
R = tank_diam/2
A_t = (pi*R**2)
A_6 = (R**2 * acos((R-6)/R) - (R-6) * sqrt(2*R*6 - 6**2))
MF = A_t / (A_t - A_6)
V = ((cut_out + 14.7)*15*max_flow*MF)/((cut_out-cut_in)*num_cycles)
if shape == 'vertical':
V += 0.0204 * tank_diam**2
return V
[docs]def bladder_size(cut_out, cut_in, num_cycles, max_flow, bladder_vol):
''' Bladder Tank sizing from the `2019 DOH Water System Design Manual`_ Equation 9-1
.. _2019 DOH Water System Design Manual: https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220
:param cut_out: nominal pump-off pressure in psi
:param cut_in: nominal pump-on pressure in psi
:param num_cycles: max number of cycles/hour/pump
:param max_flow: estimated max flow from 1 pump
:param bladder_vol: volume of bladder tank in gallons
:type cut_out: int/float
:type cut_in: int/float
:type num_cycles: int
:type max_flow: int/float
:type bladder_vol: int/float
:return: number of bladder tanks
:rtype: int
'''
R = 15*(cut_out+14.7)*(cut_in+14.7) / ((cut_out-cut_in)*(cut_in+9.7))
T = R*max_flow / (num_cycles * bladder_vol)
return ceil(T)
[docs]def air_dump_valve_size(cut_out, cut_in, tank_vol, evac_time=5, info=False, **kwargs):
'''"Air Dump" valve orifice size calculation. Sizes the minimum theoretical orifice
diameter of an air release valve to evaculate a volume of air in a given period of
time. This function assumes a starting water level in the tank at half full and a
required dump air volume when the tank is empty.
.. math::
A = \\frac{W}{C K P_1 K_b} \\sqrt{\\frac{T Z}{M}}
where A = orifice area
:param cut_out: nominal pump off pressure in psi
:param cut_in: nominal pump on pressure in psi
:param tank_vol: volume of H-PN tank in gallons
:param evac_time: time to empty entire tank in minutes *default 5*
:param info: print report *default false*
:param \**kwargs: keyword arguments
:type cut_out: int/float
:type cut_in: int/float
:type tank_vol: int/float
:type evac_time: int
:type info: boolean
:type \**kwargs: dictionary
:return: theoretical orifice size, if info==true then it will print a report
:rtype: float
:keyword arguments:
:R: (*int/float*) - ideal gas constant in ftlb/Rankine *default 53.35*
:T: (*int/float*) - air temperature in Rankine *default 527.7*
:Z: (*int/float*) - compressibility factor *default 1*
:C: (*int/float*) - gas constant based upon the ratio of specific heats *default 356*
:K: (*int/float*) - coefficient of discharge *default 0.975*
:k_b: (*int/float*) - backpressure correction factor *default 1*
:M: (*int/float*) - molecular weight of of air in lbm/lbmol *default 28.97*
'''
# Keyword arguments
R = kwargs.get('R', 53.35) # R constant in ftlb/Rankine
T = kwargs.get('T', 527.7) # Air temp in Rankine
Z = kwargs.get('Z', 1)
C = kwargs.get('C', 356) # gas constant
K = kwargs.get('K', 0.975)
k_b = kwargs.get('k_b', 1)
M = kwargs.get('M', 28.97)
# Calcs
V_tank = tank_vol / 7.481 # cuft
V_air = V_tank/2 # air vol in tank (half full)
P_avg = (cut_out + cut_in)/ 2 # avg pressure
# In No-Water Event...
P_empty = P_avg * V_air / V_tank # in psi
m = (P_empty*V_tank) / (R*T) * 144 # in lbs of air
# theoretical orifice dims
W = (m/evac_time) * 60 # mean dischage in lb/hr
A = (W * sqrt(T*Z)) / (C * K * (P_empty + 14.7) * k_b * sqrt(M))
D = sqrt(4*A/pi)
if info:
report = '''
Pressure in No-Water Event = {0:.2f} psi
Mass of Air in Tank = {1:.2f} lbs
Mean Discharge Rate = {2:.2f} lbs/hr
Theoretical Orifice Dims:
Area = {3:.3f} in^2
Diameter = {4:.3f} in
'''.format(
P_empty, m, W, A, D)
if D <= .5:
report += '\nApco Valve #200 with 1/2" diameter OK'
print(report)
return D
[docs]def pressure_relief_valve_size(cut_out, tank_vol, capacity=None, info=False, **kwargs):
''' pressure relief valve sizing calculation for ASME VIII valve on a H-PN tank
.. math::
A = \\frac{W}{C K P_1 K_b} \\sqrt{\\frac{T Z}{M}}
where A = orifice area
:param cut_out: nominal pump off pressure in psi
:type cut_out: int/float
:param tank_vol: volume of H-PN tank in gallons
:type tank_vol: int/float
:param capacity: required relieving capacity in SCFM *default None* (see note)
:type capacity: int/float
:param info: print a report of the results
:type info: boolean
:param \**kwargs: keyword arguments
:type \**kwargs: dictionary
:return: returns the minimum orifice diameter of a H-PN tank
:rtype: float
:keyword arguments:
:R: (*int/float*) - ideal gas constant in ftlb/Rankine *default 53.35*
:T: (*int/float*) - air temperature in Rankine *default = 527.7*
:Z: (*int/float*) - compressibility factor *default 1*
:K: (*int/float*) - coefficient of discharge *default 0.878*
:k_b: (*int/float*) - backpressure coefficient *default 1*
:M: molecular weight of air in lbm/lbmol *default 28.97*
if capacity is **None** then it will use the WWS standard compressor capacity
'''
R = kwargs.get('R', 53.35)
T = kwargs.get('T', 527.7)
Z = kwargs.get('Z', 1)
C = kwargs.get('C', 356)
K = kwargs.get('K', 0.878)
k_b = kwargs.get('k_b', 1)
M = kwargs.get('M', 28.97)
orifice_area = {'D' : 0.121,
'E' : 0.216,
'F' : 0.337,
'G' : 0.553,
'H' : 0.864,
'J' : 1.415}
# Calcs
V_tank = tank_vol / 7.481 # cuft
V_air = V_tank/2 # air vol in tank (half full)
P_1 = round(cut_out * 1.1)
# assuming California Air Tools Compressor flow rate
if capacity is None:
capacity = -.022*cut_out + 7.28 # CFM
# mass of air per minute
m_dot = (cut_out * capacity *144) / (R*T) # in lbs of air/min
delta_m = ((P_1-cut_out)*V_air*144) / (R*T)
m = (m_dot + delta_m) # lbs of air/min
# theoretical orifice dims
W = m * 60 # mean dischage in lb/hr
A = (W * sqrt(T*Z)) / (C * K * (P_1 + 14.7) * k_b * sqrt(M))
D = sqrt(4*A/pi)
if info:
report = '''
Pressure Setpoint = {0:.2f} psi
Volumetric Flow of Air Contribuited by compressor = {7:.2f}
Mass of air contributed by compressor = {4:.2f}
Mass of built up air to be discharged = {5:.2f}
Total Mass of Air to be Discharged = {6:.2f}
Mean Discharge Rate = {1:.2f} lbs/hr
Theoretical Orifice Dims:
Area = {2:.3f} in^2
Diameter = {3:.3f} in
'''.format(
P_1, W, A, D, m_dot, delta_m, m, capacity)
print(report)
return A
[docs]def resistance(velocity=None, headloss=None, K=None):
''' calculates resistance coefficient or headloss
:param velocity: velocity in feet per second (FPS) *default None*
:param headloss: head loss in feet of water *default None*
:param K: resistance coefficient *default None*
:type velocity: int/float
:type headloss: int/float
:type K: int/float
:return: resistance coefficient or headloss
:rtype: float
'''
if headloss and not K:
K = (2*WATER.g*headloss)/velocity**2
return K
elif K and not headloss:
headloss = K * (velocity**2/(2*WATER.g))
return headloss
else:
print('must enter headloss or K value')
[docs]def leakage(pipe_diam, test_pressure, linear_feet, hydrants=0, interties=0, valves=0, end_caps=0):
''' calculates AWWA allowable leakage for a pressure test on a water main
.. math::
L = \\frac{N d \\sqrt{P_{test}}}{7400}
:param pipe_diam: pipe diameter in inches (in)
:param test_pressure: test pressure in psi
:param linear_feet: length of pipe being tested (ft)
:param hydrants: number of hydrants *default 0*
:param interties: number of interties *default 0*
:param valves: number of valves *default 0*
:param end_caps: number of end caps *default 0*
:return: water leakage in gph and gpm
:rtype: tuple
'''
lf = linear_feet/20
hyd = hydrants * 5
vlv = valves * 2
N = lf + hyd + interties + vlv + end_caps
L_gph = N * pipe_diam * sqrt(test_pressure) / 7400
L_gpm = L_gph/60
return L_gph, L_gpm
[docs]def makeup_water(diam_before, diam_after, depth_before, depth_after):
''' Enter dimensions of frustrum or cylynder to return volume.
:param diam_before: container diameter before pumping
:param diam_after: container diameter after pumping
:param depth_before: water level before pumping
:param depth_after: water level after pumping
:type diam_before: int/float:
:type depth_after: int/float
:return: volume of water in a cylindrical or conical container
:rtype: int/float
'''
h = abs(depth_before - depth_after)
V = (pi * h * (diam_before**2 + diam_before*diam_after + diam_after**2)) / 12
return V
[docs]def wellhead_CFR(Q, H, n=0.22, t_list=[1,5,10]):
''' Returns fixed radius wellhead contribution zones (CFR) from the
`2019 DOH Water System Design Manual`_ Equation 9-1
.. _2019 DOH Water System Design Manual: https://www.doh.wa.gov/Portals/1/Documents/Pubs/331-123.pdf?ver=2019-10-03-153237-220
:param Q: pumping rate in cubic ft/yr
:param H: well open interval in ft
:param n: aquifer porosity *default 0.22*
:param t_list: times in years *default [1, 5, 10]*
:type Q: int/float
:type H: int/float
:type n: float
:type t_list: list
:return: radii of well contribution zones for listed years
:rtype: list
'''
r = [sqrt(Q*t/(pi*n*H)) for t in t_list]
return r
[docs]def max_pump_elevation(elevation, NPSHr, Losses, SF=1.5, **kwargs):
'''Returns maximum elevation pump suction can be above water level
:param elevation: elevation of pump in ft
:param NPSHr: net positive suction head required in ft
:param Losses: suction side head loss in ft
:param SF: safety factor *default 1.5*
:param \**kwargs: keyword arguments
:type elevation: int/float
:type NPSHr: int/float
:type Losses: int/float
:type SF: int/float
:type \**kwargs: dictionary
:return: maximum pump elevation ft
:rtype: int/float
:keyword arguments:
:Pb: (*int/float*) - barometric pressure in inches Hg *default 29.92126*
:Tb: (*int/float*) - temperature in Kelvin *default 288.15*
:R: (*int/float*) - R constant in lbft^2 *default 89494.56*
:g: (*int/float*) - gravity in ft/s^2 *default 32.17405*
:M: (*int/float*) - molar weight of air in lb/lb-mol *default 28.9644*
:Pv: (*int/float*) - vapor pressure of water at 50F in feet *default 0.75*
Negative number indicates ft of head that must be supplied
to suction line.
Positive number indicates how far pump can be above water level.
'''
# Barometric Pressure Constants
Pb = kwargs.get('Pb', 29.92126) # in. Hg
Tb = kwargs.get('Tb', 288.15) # K
R = kwargs.get('R', 8.9494596*10**4) # lb·ft^2
g = kwargs.get('g', 32.17405) #ft/s^2
M = kwargs.get('M', 28.9644) # lb/lb-mol
Pv = kwargs.get('Pv', 0.75) # vapor pressure of water at 50F in ft
# atm pressure at elevation
P = Pb*exp((-g*M*elevation)/(R*Tb))
# convert inches Hg to ft of head
P = P*1.132925
# max pump height
Z = P - NPSHr - Losses - Pv - SF
return Z
########## Test Script ############
if __name__=="__main__":
print('test script:')
# Peak Hour Demand Calcs
phd= PHD(100, 75)
phd2 = PHD(50, 200)
# Horse Power Calcs
water_p, break_p, input_p = calc_hp(100, 120, 0.65, 0.95)
water2_p, _, _ = calc_hp(230,50)
# Flow and Velocity Calcs
Q = 50 # gpm
d = 6 # inches
v = velocity(Q, d)
q_func = flow(v, d)
d_func = pipeDiameter(Q,v)
# Reynolds Number
Re = reynolds(d, vel=v)
Re_q = reynolds(d, flow=Q)
# Volume Calculations
vol1 = volume_cyl(5, 10)
vol2 = volume_box(5, 10, 20)
# cubic feet to gallon conversion
gals = cuft2gal(1000)
# allowable leakage calc
leak_gph, leak_gpm = leakage(8, 245, 1460, 1, 2, 3)
# makeup water volume (volume of a frustrum)
mw = makeup_water(18, 17.5, 19, 18)
# bladder tank sizing
bt = bladder_size(86, 67, 6, 90, 34)
# output string
out = '''
PHD = {0:.2f} gpm
PHD2_raw = {1:f}
hp_w1 = {2:.2f} hp
hp_b1 = {3:.2f} hp
hp_i1 = {4:.2f} hp
hp_raw = {5:f}
flow input = {6:.1f} gpm
pipe diameter input = {7:.1f} in
calculated velocity = {8:.2f} fps
calculated flow = {9:.2f} gpm \r
calculated diameter = {10:.2f} in
Reynolds Number = {11:.0f}
Reynolds Number given flow = {12:.0f}
vol1 = {13:f}
vol2 = {14:.2f}
gallons = {15:.2f}
allowable leakage = {16:.2f} gph or {17:.3f} gpm
makeup water = {18:.3f} cubic inches or {19:.3f} gals
number of bladder tanks = {20:.1f} tanks
'''.format(
phd, phd2, water_p, break_p, input_p,
water2_p, Q, d, v, q_func, d_func, Re,
Re_q, vol1, vol2, gals, leak_gph,
leak_gpm, mw, cuin2gal(mw), bt)
print(out)
pressure_relief_valve_size(95, 500, info=True)