예제 #1
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()
    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(default={"solute_list": ["nitrogen"]})
    m.fs.costing = ZeroOrderCosting()
    m.fs.unit = PhotothermalMembraneZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(120)
    m.fs.unit.inlet.flow_mass_comp[0, "nitrogen"].fix(1)
    m.fs.unit.load_parameters_from_database(use_default_removal=True)

    assert degrees_of_freedom(m.fs.unit) == 0

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.photothermal_membrane, Block)
    assert isinstance(m.fs.costing.photothermal_membrane.membrane_cost, Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0
    initialization_tester(m)

    assert pytest.approx(4.719596,
                         rel=1e-5) == value(m.fs.unit.costing.capital_cost)
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(default={"solute_list": ["sulfur", "toc", "tss"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = PumpElectricityZO(
        default={"property_package": m.fs.params, "database": m.db}
    )

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(1e-5)
    m.fs.unit1.inlet.flow_mass_comp[0, "sulfur"].fix(10)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(20)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(30)
    m.fs.unit1.load_parameters_from_database()
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing}
    )

    assert isinstance(m.fs.costing.pump_electricity, Block)
    assert isinstance(m.fs.costing.pump_electricity.pump_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows["electricity"]
예제 #3
0
def test_costing():

    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(default={"solute_list": ["tss"]})

    m.fs.unit = FilterPressZO(
        default={"property_package": m.fs.params, "database": m.db}
    )

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "tss"].fix(23)

    m.fs.costing = ZeroOrderCosting()
    m.fs.unit.load_parameters_from_database()

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing}
    )

    assert isinstance(m.fs.costing.filter_press, Block)
    assert isinstance(m.fs.costing.filter_press.capital_a_parameter, Var)
    assert isinstance(m.fs.costing.filter_press.capital_b_parameter, Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0

    assert m.fs.unit.electricity[0] in m.fs.costing._registered_flows["electricity"]
예제 #4
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["tss", "sulfate", "foo", "bar"]})
    m.fs.costing = ZeroOrderCosting()
    m.fs.unit = InjectionWellDisposalZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })
    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})
    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(123)
    m.fs.unit.inlet.flow_mass_comp[0, "tss"].fix(4)
    m.fs.unit.inlet.flow_mass_comp[0, "sulfate"].fix(0.005)
    m.fs.unit.inlet.flow_mass_comp[0, "foo"].fix(0.67)
    m.fs.unit.inlet.flow_mass_comp[0, "bar"].fix(8.9)
    m.fs.unit.load_parameters_from_database()

    assert degrees_of_freedom(m.fs.unit) == 0
    initialization_tester(m)
    results = solver.solve(m)
    assert_optimal_termination(results)

    assert isinstance(m.fs.costing.injection_well_disposal, Block)
    assert isinstance(m.fs.costing.injection_well_disposal.capital_a_parameter,
                      Var)
    assert isinstance(m.fs.costing.injection_well_disposal.capital_b_parameter,
                      Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["nitrogen", "phosphorus", "struvite", "foo"]})

    source_file = os.path.join(
        os.path.dirname(os.path.abspath(__file__)),
        "..",
        "..",
        "..",
        "examples",
        "flowsheets",
        "case_studies",
        "wastewater_resource_recovery",
        "electrochemical_nutrient_removal",
        "case_1617.yaml",
    )

    m.fs.costing = ZeroOrderCosting(
        default={"case_study_definition": source_file})

    m.fs.unit = ElectroNPZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(1000)
    m.fs.unit.inlet.flow_mass_comp[0, "nitrogen"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "phosphorus"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "struvite"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "foo"].fix(1)
    m.fs.unit.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit) == 0

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.electrochemical_nutrient_removal, Block)
    assert isinstance(m.fs.costing.electrochemical_nutrient_removal.HRT, Var)
    assert isinstance(
        m.fs.costing.electrochemical_nutrient_removal.sizing_cost, Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0
    initialization_tester(m)
    results = solver.solve(m)
    assert_optimal_termination(results)

    assert m.fs.unit.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
    assert (m.fs.unit.MgCl2_flowrate[0]
            in m.fs.costing._registered_flows["magnesium_chloride"])
예제 #6
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["sulfur", "toc", "tss"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = FixedBedZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "sulfur"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.fixed_bed, Block)
    assert isinstance(m.fs.costing.fixed_bed.capital_a_parameter, Var)
    assert isinstance(m.fs.costing.fixed_bed.capital_b_parameter, Var)
    assert isinstance(m.fs.costing.fixed_bed.reference_state, Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
    assert (m.fs.unit1.acetic_acid_demand[0]
            in m.fs.costing._registered_flows["acetic_acid"])
    assert (m.fs.unit1.phosphoric_acid_demand[0]
            in m.fs.costing._registered_flows["phosphoric_acid"])
    assert (m.fs.unit1.ferric_chloride_demand[0]
            in m.fs.costing._registered_flows["ferric_chloride"])
    assert (m.fs.unit1.activated_carbon_demand[0]
            in m.fs.costing._registered_flows["activated_carbon"])
    assert m.fs.unit1.sand_demand[0] in m.fs.costing._registered_flows["sand"]
    assert (m.fs.unit1.anthracite_demand[0]
            in m.fs.costing._registered_flows["anthracite"])
    assert (m.fs.unit1.cationic_polymer_demand[0]
            in m.fs.costing._registered_flows["cationic_polymer"])
예제 #7
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["iron", "manganese", "foo"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = IronManganeseRemovalZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "iron"].fix(250)
    m.fs.unit1.inlet.flow_mass_comp[0, "manganese"].fix(250)
    m.fs.unit1.inlet.flow_mass_comp[0, "foo"].fix(1)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.iron_and_manganese_removal, Block)
    assert isinstance(
        m.fs.costing.iron_and_manganese_removal.capital_blower_a_parameter,
        Var)
    assert isinstance(
        m.fs.costing.iron_and_manganese_removal.capital_backwash_a_parameter,
        Var)
    assert isinstance(
        m.fs.costing.iron_and_manganese_removal.capital_backwash_b_parameter,
        Var)
    assert isinstance(
        m.fs.costing.iron_and_manganese_removal.capital_filter_a_parameter,
        Var)
    assert isinstance(
        m.fs.costing.iron_and_manganese_removal.capital_filter_b_parameter,
        Var)
    assert isinstance(m.fs.costing.iron_and_manganese_removal.flow_exponent,
                      Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
예제 #8
0
    def model(self):
        m = ConcreteModel()
        m.db = Database()

        m.fs = FlowsheetBlock(default={"dynamic": False})

        m.fs.params = WaterParameterBlock(
            default={"solute_list": ["sulfur", "toc", "tss"]})

        m.fs.costing = ZeroOrderCosting()

        return m
예제 #9
0
    def model(self):
        m = ConcreteModel()

        m.frame = ZeroOrderCosting()

        # Dummy a unit model to use with _get_tech_parameters
        m.dummy_unit = Block(concrete=True)
        m.dummy_unit.config = ConfigBlock()
        m.dummy_unit.config.declare("flowsheet_costing_block", ConfigValue())
        m.dummy_unit.config.flowsheet_costing_block = m.frame
        add_object_reference(m.dummy_unit, "unit_model", m.dummy_unit)
        m.dummy_unit._tech_type = "test_tech"

        return m
예제 #10
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["sulfur", "toc", "tds"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = IonExchangeZO(default={
        "property_package": m.fs.params,
        "database": m.db,
        "process_subtype": subtype})

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "sulfur"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "tds"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(default={
        "flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.ion_exchange, Block)
    assert isinstance(m.fs.costing.ion_exchange.capital_a_parameter,
                      Var)
    assert isinstance(m.fs.costing.ion_exchange.capital_b_parameter,
                      Var)
    assert isinstance(m.fs.costing.ion_exchange.capital_c_parameter,
                      Var)
    assert isinstance(m.fs.costing.ion_exchange.capital_d_parameter,
                      Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint,
                      Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in \
        m.fs.costing._registered_flows["electricity"]

    assert m.fs.unit1.NaCl_flowrate[0] in \
        m.fs.costing._registered_flows["sodium_chloride"]
    assert m.fs.unit1.resin_demand[0] in \
        m.fs.costing._registered_flows["ion_exchange_resin"]
예제 #11
0
def test_costing_non_default_subtype():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(default={"solute_list": ["tds", "dye"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit = NanofiltrationZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": "rHGO_dye_rejection",
        }
    )

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit.inlet.flow_mass_comp[0, "tds"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "dye"].fix(2)

    m.fs.unit.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit) == 0

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing}
    )

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)
    assert isinstance(m.fs.costing.nanofiltration, Block)
    assert isinstance(m.fs.unit.costing.variable_operating_cost, Var)
    assert isinstance(m.fs.unit.costing.variable_operating_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0

    initialization_tester(m)

    results = solver.solve(m)

    # Check for optimal solution
    assert check_optimal_termination(results)

    assert pytest.approx(39162.813807, rel=1e-5) == value(m.fs.unit.area)
    assert pytest.approx(0.58744, rel=1e-5) == value(m.fs.unit.costing.capital_cost)
    assert pytest.approx(0.088116, rel=1e-5) == value(
        m.fs.unit.costing.variable_operating_cost
    )
예제 #12
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(default={"solute_list": ["sulfur", "toc", "tss"]})
    m.fs.costing = ZeroOrderCosting()
    m.fs.unit = LandfillZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        }
    )

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(1e-5)
    m.fs.unit.inlet.flow_mass_comp[0, "sulfur"].fix(1000)
    m.fs.unit.inlet.flow_mass_comp[0, "toc"].fix(2000)
    m.fs.unit.inlet.flow_mass_comp[0, "tss"].fix(3000)

    m.fs.unit.load_parameters_from_database()

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing}
    )

    assert isinstance(m.fs.costing.landfill, Block)
    assert isinstance(m.fs.costing.landfill.capital_a_parameter, Var)
    assert isinstance(m.fs.costing.landfill.capital_b_parameter, Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)
    assert_units_consistent(m.fs)

    assert degrees_of_freedom(m.fs.unit) == 0

    initialization_tester(m)
    _ = solver.solve(m)

    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    if subtype == "default":
        assert pytest.approx(43.5627, rel=1e-5) == value(m.fs.unit.costing.capital_cost)
    if subtype == "landfill_zld":
        assert pytest.approx(20.09155, rel=1e-5) == value(
            m.fs.unit.costing.capital_cost
        )

    assert m.fs.unit.electricity[0] in m.fs.costing._registered_flows["electricity"]
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(
        default={
            "solute_list":
            ["tds", "magnesium", "calcium", "nitrate", "sulfate", "tss"]
        })
    m.fs.costing = ZeroOrderCosting()
    m.fs.unit = EvaporationPondZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(10)
    m.fs.unit.inlet.flow_mass_comp[0, "tds"].fix(123)
    m.fs.unit.inlet.flow_mass_comp[0, "magnesium"].fix(456)
    m.fs.unit.inlet.flow_mass_comp[0, "calcium"].fix(789)
    m.fs.unit.inlet.flow_mass_comp[0, "nitrate"].fix(10)
    m.fs.unit.inlet.flow_mass_comp[0, "sulfate"].fix(11)
    m.fs.unit.inlet.flow_mass_comp[0, "tss"].fix(12)
    m.fs.unit.load_parameters_from_database(use_default_removal=True)

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.evaporation_pond, Block)
    assert isinstance(m.fs.costing.evaporation_pond.cost_per_acre_a_parameter,
                      Var)
    assert isinstance(m.fs.costing.evaporation_pond.cost_per_acre_b_parameter,
                      Var)
    assert isinstance(m.fs.costing.evaporation_pond.cost_per_acre_c_parameter,
                      Var)
    assert isinstance(m.fs.costing.evaporation_pond.cost_per_acre_d_parameter,
                      Var)
    assert isinstance(m.fs.costing.evaporation_pond.cost_per_acre_e_parameter,
                      Var)
    assert isinstance(m.fs.costing.evaporation_pond.liner_thickness, Var)
    assert isinstance(m.fs.costing.evaporation_pond.land_cost, Var)
    assert isinstance(m.fs.costing.evaporation_pond.land_clearing_cost, Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0
예제 #14
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["toc", "nitrate", "sulfate", "bar", "crux"]}
    )
    m.fs.costing = ZeroOrderCosting()
    m.fs.unit = WellFieldZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        }
    )

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(120)
    m.fs.unit.inlet.flow_mass_comp[0, "toc"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "nitrate"].fix(2)
    m.fs.unit.inlet.flow_mass_comp[0, "sulfate"].fix(0.3)
    m.fs.unit.inlet.flow_mass_comp[0, "bar"].fix(40)
    m.fs.unit.inlet.flow_mass_comp[0, "crux"].fix(0.0005)

    m.fs.unit.load_parameters_from_database()

    assert degrees_of_freedom(m.fs.unit) == 0
    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing}
    )
    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0
    initialization_tester(m)
    _ = solver.solve(m)

    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    if subtype == "default":
        assert pytest.approx(1.665893, rel=1e-5) == value(
            m.fs.unit.costing.capital_cost
        )
    if subtype == "emwd":
        assert pytest.approx(47.921893, rel=1e-5) == value(
            m.fs.unit.costing.capital_cost
        )

    assert m.fs.unit.electricity[0] in m.fs.costing._registered_flows["electricity"]
예제 #15
0
def add_costing(m):
    source_file = os.path.join(
        os.path.dirname(os.path.abspath(__file__)),
        "biomembrane_filtration_global_costing.yaml",
    )
    m.fs.costing = ZeroOrderCosting(
        default={"case_study_definition": source_file})
    # typing aid
    costing_kwargs = {"default": {"flowsheet_costing_block": m.fs.costing}}
    m.fs.mabr.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.dmbr.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.pump.costing = UnitModelCostingBlock(**costing_kwargs)

    m.fs.costing.cost_process()
    m.fs.costing.add_electricity_intensity(
        m.fs.product_H2O.properties[0].flow_vol)
    m.fs.costing.add_LCOW(m.fs.product_H2O.properties[0].flow_vol)
예제 #16
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["viruses_enteric", "toc", "cryptosporidium"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = UVAOPZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "viruses_enteric"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "cryptosporidium"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)

    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.unit1.chemical_flow_mass, Var)
    assert isinstance(m.fs.costing.uv_aop, Block)
    assert isinstance(m.fs.costing.uv_aop.uv_capital_a_parameter, Var)
    assert isinstance(m.fs.costing.uv_aop.uv_capital_b_parameter, Var)
    assert isinstance(m.fs.costing.uv_aop.uv_capital_c_parameter, Var)
    assert isinstance(m.fs.costing.uv_aop.uv_capital_d_parameter, Var)
    assert isinstance(m.fs.costing.uv_aop.aop_capital_a_parameter, Var)
    assert isinstance(m.fs.costing.uv_aop.aop_capital_b_parameter, Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
    assert str(m.fs.costing._registered_flows["hydrogen_peroxide"][0]) == str(
        m.fs.unit1.chemical_flow_mass[0])
def test_costing(subtype):
    print(subtype)
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["sulfur", "toc", "tss"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = ChemicalAdditionZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "sulfur"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.chemical_addition, Block)
    assert isinstance(m.fs.costing.chemical_addition.capital_a_parameter, Var)
    assert isinstance(m.fs.costing.chemical_addition.capital_b_parameter, Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]

    assert str(m.fs.unit1.chemical_dosage[0] *
               m.fs.unit1.properties[0].flow_vol /
               m.fs.unit1.ratio_in_solution) == str(
                   m.fs.costing._registered_flows[subtype][0])
예제 #18
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["sulfur", "toc", "tss"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = SecondaryTreatmentWWTPZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "sulfur"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.secondary_treatment_wwtp, Block)
    assert isinstance(
        m.fs.costing.secondary_treatment_wwtp.capital_a_parameter, Var)
    assert isinstance(
        m.fs.costing.secondary_treatment_wwtp.capital_b_parameter, Var)
    assert isinstance(m.fs.costing.secondary_treatment_wwtp.reference_state,
                      Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
예제 #19
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()
    m.fs = FlowsheetBlock(default={"dynamic": False})
    m.fs.params = WaterParameterBlock(
        default={
            "solute_list": [
                "nitrogen",
                "phosphates",
                "bioconcentrated_phosphorous",
                "nitrous_oxide",
            ]
        }
    )
    m.fs.costing = ZeroOrderCosting()
    m.fs.unit = CANDOPZO(default={"property_package": m.fs.params, "database": m.db})

    m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(120)
    m.fs.unit.inlet.flow_mass_comp[0, "nitrogen"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "phosphates"].fix(1)
    m.fs.unit.inlet.flow_mass_comp[0, "bioconcentrated_phosphorous"].fix(0)
    m.fs.unit.inlet.flow_mass_comp[0, "nitrous_oxide"].fix(0)
    m.fs.unit.load_parameters_from_database(use_default_removal=True)

    assert degrees_of_freedom(m.fs.unit) == 0

    m.fs.unit.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing}
    )

    assert isinstance(m.fs.costing.CANDO_P, Block)
    assert isinstance(m.fs.costing.CANDO_P.sizing_parameter, Var)
    assert isinstance(m.fs.costing.CANDO_P.sizing_cost, Var)

    assert isinstance(m.fs.unit.costing.capital_cost, Var)
    assert isinstance(m.fs.unit.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit) == 0
    initialization_tester(m)

    assert pytest.approx(42.651167, rel=1e-5) == value(m.fs.unit.costing.capital_cost)

    assert m.fs.unit.electricity[0] in m.fs.costing._registered_flows["electricity"]
예제 #20
0
    def model(self):
        m = ConcreteModel()
        m.db = Database()

        m.fs = FlowsheetBlock(default={"dynamic": False})
        m.fs.params = WaterParameterBlock(
            default={"solute_list": ["cod", "methane"]})

        source_file = os.path.join(
            os.path.dirname(os.path.abspath(__file__)),
            "..",
            "..",
            "..",
            "examples",
            "flowsheets",
            "case_studies",
            "wastewater_resource_recovery",
            "metab",
            "metab_global_costing.yaml",
        )
        m.fs.costing = ZeroOrderCosting(
            default={"case_study_definition": source_file})

        m.fs.unit = MetabZO(
            default={
                "property_package": m.fs.params,
                "database": m.db,
                "process_subtype": "methane",
            })

        m.fs.unit.inlet.flow_mass_comp[0, "H2O"].fix(1)
        m.fs.unit.inlet.flow_mass_comp[0, "cod"].fix(0.01)
        m.fs.unit.inlet.flow_mass_comp[0, "methane"].fix(0)

        m.db.get_unit_operation_parameters("metab")
        m.fs.unit.load_parameters_from_database(use_default_removal=True)

        m.fs.unit.costing = UnitModelCostingBlock(
            default={"flowsheet_costing_block": m.fs.costing})

        m.fs.costing.cost_process()

        return m
예제 #21
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["tds", "toc", "tss"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = ElectrodialysisReversalZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "tds"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.electrodialysis_reversal, Block)
    assert isinstance(
        m.fs.costing.electrodialysis_reversal.capital_a_parameter, Var)
    assert isinstance(
        m.fs.costing.electrodialysis_reversal.capital_b_parameter, Var)
    assert isinstance(m.fs.costing.electrodialysis_reversal.reference_state,
                      Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
예제 #22
0
def test_costing():
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(default={
        "solute_list": ["bod", "tss", "ammonium_as_nitrogen", "nitrate"]
    })

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = MABRZO(default={
        "property_package": m.fs.params,
        "database": m.db
    })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10)
    m.fs.unit1.inlet.flow_mass_comp[0, "bod"].fix(5)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(5)
    m.fs.unit1.inlet.flow_mass_comp[0, "ammonium_as_nitrogen"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "nitrate"].fix(1)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.mabr, Block)
    assert isinstance(m.fs.costing.mabr.specific_removal, Var)
    assert isinstance(m.fs.costing.mabr.reactor_cost, Var)
    assert isinstance(m.fs.costing.mabr.specific_air_flow, Var)
    assert isinstance(m.fs.costing.mabr.blower_cost, Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
예제 #23
0
def add_costing(m):
    m.fs.costing = ZeroOrderCosting()
    # typing aid
    costing_kwargs = {"default": {"flowsheet_costing_block": m.fs.costing}}
    m.fs.intake_pump.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.coag_and_floc.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.sedimentation.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.ozonation.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.gravity_basin.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.gac.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.backwash_pump.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.uv.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.anion_exchange.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.chlorination.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.storage.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.recharge_pump.costing = UnitModelCostingBlock(**costing_kwargs)

    m.fs.costing.cost_process()
    m.fs.costing.add_electricity_intensity(m.fs.product.properties[0].flow_vol)
    m.fs.costing.add_LCOW(m.fs.product.properties[0].flow_vol)
예제 #24
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(default={"solute_list": ["foo"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = WaterPumpingStationZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "foo"].fix(1)

    m.fs.unit1.load_parameters_from_database()
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.water_pumping_station, Block)
    assert isinstance(m.fs.costing.water_pumping_station.capital_a_parameter,
                      Var)
    assert isinstance(m.fs.costing.water_pumping_station.capital_b_parameter,
                      Var)
    assert isinstance(m.fs.costing.water_pumping_station.reference_state, Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0

    assert m.fs.unit1.electricity[0] in m.fs.costing._registered_flows[
        "electricity"]
예제 #25
0
def test_costing(subtype):
    m = ConcreteModel()
    m.db = Database()

    m.fs = FlowsheetBlock(default={"dynamic": False})

    m.fs.params = WaterParameterBlock(
        default={"solute_list": ["sulfur", "toc", "tss"]})

    m.fs.costing = ZeroOrderCosting()

    m.fs.unit1 = StorageTankZO(
        default={
            "property_package": m.fs.params,
            "database": m.db,
            "process_subtype": subtype,
        })

    m.fs.unit1.inlet.flow_mass_comp[0, "H2O"].fix(10000)
    m.fs.unit1.inlet.flow_mass_comp[0, "sulfur"].fix(1)
    m.fs.unit1.inlet.flow_mass_comp[0, "toc"].fix(2)
    m.fs.unit1.inlet.flow_mass_comp[0, "tss"].fix(3)
    m.fs.unit1.load_parameters_from_database(use_default_removal=True)
    assert degrees_of_freedom(m.fs.unit1) == 0

    m.fs.unit1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.costing})

    assert isinstance(m.fs.costing.storage_tank, Block)
    assert isinstance(m.fs.costing.storage_tank.capital_a_parameter, Var)
    assert isinstance(m.fs.costing.storage_tank.capital_b_parameter, Var)

    assert isinstance(m.fs.unit1.costing.capital_cost, Var)
    assert isinstance(m.fs.unit1.costing.capital_cost_constraint, Constraint)

    assert_units_consistent(m.fs)
    assert degrees_of_freedom(m.fs.unit1) == 0
예제 #26
0
def add_costing(m):
    prtrt = m.fs.pretreatment
    desal = m.fs.desalination
    psttrt = m.fs.posttreatment

    # Add costing package for zero-order units
    m.fs.zo_costing = ZeroOrderCosting()
    m.fs.ro_costing = WaterTAPCosting()

    # Add costing to zero order units
    # Pre-treatment units
    # This really looks like it should be a feed block in its own right
    # prtrt.intake.costing = UnitModelCostingBlock(default={
    #     "flowsheet_costing_block": m.fs.zo_costing})

    prtrt.ferric_chloride_addition.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.chlorination.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.static_mixer.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.storage_tank_1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.media_filtration.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.backwash_handling.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.anti_scalant_addition.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    prtrt.cartridge_filtration.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )

    # RO Train
    # RO equipment is costed using more detailed costing package
    desal.P1.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.ro_costing}
    )
    desal.RO.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.ro_costing}
    )
    if m.erd_type == "pressure_exchanger":
        # desal.S1.costing = UnitModelCostingBlock(default={
        #     "flowsheet_costing_block": m.fs.ro_costing})
        desal.M1.costing = UnitModelCostingBlock(
            default={"flowsheet_costing_block": m.fs.ro_costing}
        )
        desal.PXR.costing = UnitModelCostingBlock(
            default={"flowsheet_costing_block": m.fs.ro_costing}
        )
        desal.P2.costing = UnitModelCostingBlock(
            default={"flowsheet_costing_block": m.fs.ro_costing}
        )
    elif m.erd_type == "pump_as_turbine":
        pass
        # desal.ERD.costing = UnitModelCostingBlock(default={
        #     "flowsheet_costing_block": m.fs.ro_costing})
    else:
        raise ConfigurationError(
            f"erd_type was {m.erd_type}, costing only implemented "
            "for pressure_exchanger or pump_as_turbine"
        )

    # For non-zero order unit operations, we need to register costed flows
    # separately.
    # However, to keep costs consistent, we will register these with the ZO
    # Costing package
    m.fs.zo_costing.cost_flow(desal.P1.work_mechanical[0], "electricity")
    if m.erd_type == "pressure_exchanger":
        m.fs.zo_costing.cost_flow(desal.P2.work_mechanical[0], "electricity")
    elif m.erd_type == "pump_as_turbine":
        pass
        # m.fs.zo_costing.cost_flow(
        #     desal.ERD.work_mechanical[0], "electricity")
    else:
        raise ConfigurationError(
            f"erd_type was {m.erd_type}, costing only implemented "
            "for pressure_exchanger or pump_as_turbine"
        )

    # Post-treatment units
    psttrt.storage_tank_2.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    psttrt.uv_aop.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    psttrt.co2_addition.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    psttrt.lime_addition.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    psttrt.storage_tank_3.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )

    # Product and disposal
    m.fs.municipal.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )
    m.fs.landfill.costing = UnitModelCostingBlock(
        default={"flowsheet_costing_block": m.fs.zo_costing}
    )

    # Aggregate unit level costs and calculate overall process costs
    m.fs.zo_costing.cost_process()
    m.fs.ro_costing.cost_process()

    # Combine results from costing packages and calculate overall metrics
    @m.Expression()
    def total_capital_cost(b):
        return (
            pyunits.convert(
                m.fs.zo_costing.total_capital_cost, to_units=pyunits.USD_2018
            )
            + m.fs.ro_costing.total_investment_cost
        )

    @m.Expression()
    def total_operating_cost(b):
        return (
            pyunits.convert(
                m.fs.zo_costing.total_fixed_operating_cost,
                to_units=pyunits.USD_2018 / pyunits.year,
            )
            + pyunits.convert(
                m.fs.zo_costing.total_variable_operating_cost,
                to_units=pyunits.USD_2018 / pyunits.year,
            )
            + m.fs.ro_costing.total_operating_cost
        )

    @m.Expression()
    def LCOW(b):
        return (
            b.total_capital_cost * b.fs.zo_costing.capital_recovery_factor
            + b.total_operating_cost
        ) / (
            pyunits.convert(
                b.fs.municipal.properties[0].flow_vol,
                to_units=pyunits.m**3 / pyunits.year,
            )
            * b.fs.zo_costing.utilization_factor
        )

    assert_units_consistent(m)
예제 #27
0
def add_costing(m):
    source_file = os.path.join(
        os.path.dirname(os.path.abspath(__file__)),
        "metab_global_costing.yaml",
    )
    m.fs.costing = ZeroOrderCosting(
        default={"case_study_definition": source_file})
    # typing aid
    costing_kwargs = {"default": {"flowsheet_costing_block": m.fs.costing}}
    m.fs.metab_hydrogen.costing = UnitModelCostingBlock(**costing_kwargs)
    m.fs.metab_methane.costing = UnitModelCostingBlock(**costing_kwargs)

    m.fs.costing.cost_process()
    m.fs.costing.add_electricity_intensity(
        m.fs.product_H2O.properties[0].flow_vol)

    # m.fs.costing.add_LCOW(m.fs.product_H2O.properties[0].flow_vol)

    # other levelized costs
    # TODO -resolve discrepancy between sum of cost components and total levelized costs
    m.fs.costing.annual_water_production = Expression(
        expr=m.fs.costing.utilization_factor * pyunits.convert(
            m.fs.product_H2O.properties[0].flow_vol,
            to_units=pyunits.m**3 / m.fs.costing.base_period,
        ))
    m.fs.costing.annual_cod_removal = Expression(
        expr=(m.fs.costing.utilization_factor * pyunits.convert(
            m.fs.feed.outlet.flow_mass_comp[0, "cod"] -
            m.fs.product_H2O.inlet.flow_mass_comp[0, "cod"],
            to_units=pyunits.kg / m.fs.costing.base_period,
        )))
    m.fs.costing.annual_hydrogen_production = Expression(
        expr=(m.fs.costing.utilization_factor * pyunits.convert(
            m.fs.metab_hydrogen.byproduct.flow_mass_comp[0, "hydrogen"],
            to_units=pyunits.kg / m.fs.costing.base_period,
        )))
    m.fs.costing.annual_methane_production = Expression(
        expr=(m.fs.costing.utilization_factor * pyunits.convert(
            m.fs.metab_methane.byproduct.flow_mass_comp[0, "methane"],
            to_units=pyunits.kg / m.fs.costing.base_period,
        )))
    m.fs.costing.total_annualized_cost = Expression(
        expr=(m.fs.costing.total_capital_cost *
              m.fs.costing.capital_recovery_factor +
              m.fs.costing.total_operating_cost))

    m.fs.costing.LCOW = Expression(
        expr=(m.fs.costing.total_annualized_cost /
              m.fs.costing.annual_water_production),
        doc="Levelized Cost of Water",
    )

    m.fs.costing.LCOCR = Expression(
        expr=(m.fs.costing.total_annualized_cost /
              m.fs.costing.annual_cod_removal),
        doc="Levelized Cost of COD Removal",
    )

    m.fs.costing.LCOH = Expression(
        expr=((
            m.fs.metab_hydrogen.costing.capital_cost *
            m.fs.costing.capital_recovery_factor +
            m.fs.metab_hydrogen.costing.capital_cost *
            m.fs.costing.maintenance_costs_percent_FCI +
            m.fs.metab_hydrogen.costing.fixed_operating_cost +
            (pyunits.convert(
                m.fs.metab_hydrogen.heat[0] * m.fs.costing.heat_cost,
                to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
            ) + pyunits.convert(
                m.fs.metab_hydrogen.electricity[0] *
                m.fs.costing.electricity_cost,
                to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
            )) * m.fs.costing.utilization_factor) /
              m.fs.costing.annual_hydrogen_production),
        doc="Levelized Cost of Hydrogen",
    )

    m.fs.costing.LCOM = Expression(
        expr=((
            m.fs.metab_methane.costing.capital_cost *
            m.fs.costing.capital_recovery_factor +
            m.fs.metab_methane.costing.capital_cost *
            m.fs.costing.maintenance_costs_percent_FCI +
            m.fs.metab_methane.costing.fixed_operating_cost + (pyunits.convert(
                m.fs.metab_methane.heat[0] * m.fs.costing.heat_cost,
                to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
            ) + pyunits.convert(
                m.fs.metab_methane.electricity[0] *
                m.fs.costing.electricity_cost,
                to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
            )) * m.fs.costing.utilization_factor) /
              m.fs.costing.annual_methane_production),
        doc="Levelized Cost of Methane",
    )

    m.fs.costing.LC_comp = Set(initialize=[
        "bead",
        "reactor",
        "mixer",
        "membrane",
        "vacuum",
        "heat",
        "electricity_mixer",
        "electricity_vacuum",
        "hydrogen_product",
        "methane_product",
    ])
    m.fs.costing.LCOH_comp = Expression(m.fs.costing.LC_comp)

    m.fs.costing.LCOH_comp["bead"] = (
        m.fs.metab_hydrogen.costing.DCC_bead * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI) +
        m.fs.metab_hydrogen.costing.fixed_operating_cost
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["reactor"] = (
        m.fs.metab_hydrogen.costing.DCC_reactor * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["mixer"] = (
        m.fs.metab_hydrogen.costing.DCC_mixer * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["vacuum"] = (
        m.fs.metab_hydrogen.costing.DCC_vacuum * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["membrane"] = (
        m.fs.metab_hydrogen.costing.DCC_membrane * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["electricity_vacuum"] = (
        pyunits.convert(
            m.fs.metab_hydrogen.energy_electric_vacuum_flow_vol_byproduct *
            m.fs.metab_hydrogen.properties_byproduct[0].
            flow_mass_comp["hydrogen"] * m.fs.costing.electricity_cost,
            to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
        ) * m.fs.costing.utilization_factor
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["electricity_mixer"] = (
        pyunits.convert(
            m.fs.metab_hydrogen.energy_electric_mixer_vol *
            m.fs.metab_hydrogen.volume * m.fs.costing.electricity_cost,
            to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
        ) * m.fs.costing.utilization_factor
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOH_comp["heat"] = (
        pyunits.convert(
            m.fs.metab_hydrogen.heat[0] * m.fs.costing.heat_cost,
            to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
        ) * m.fs.costing.utilization_factor
    ) / m.fs.costing.annual_hydrogen_production

    m.fs.costing.LCOM_comp = Expression(m.fs.costing.LC_comp)

    m.fs.costing.LCOM_comp["bead"] = (
        m.fs.metab_methane.costing.DCC_bead * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI) +
        m.fs.metab_methane.costing.fixed_operating_cost
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["reactor"] = (
        m.fs.metab_methane.costing.DCC_reactor * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["mixer"] = (
        m.fs.metab_methane.costing.DCC_mixer * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["vacuum"] = (
        m.fs.metab_methane.costing.DCC_vacuum * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["membrane"] = (
        m.fs.metab_methane.costing.DCC_membrane * m.fs.costing.TIC *
        (m.fs.costing.capital_recovery_factor +
         m.fs.costing.maintenance_costs_percent_FCI)
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["electricity_vacuum"] = (
        pyunits.convert(
            m.fs.metab_methane.energy_electric_vacuum_flow_vol_byproduct *
            m.fs.metab_methane.properties_byproduct[0].
            flow_mass_comp["methane"] * m.fs.costing.electricity_cost,
            to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
        ) * m.fs.costing.utilization_factor
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["electricity_mixer"] = (
        pyunits.convert(
            m.fs.metab_methane.energy_electric_mixer_vol *
            m.fs.metab_methane.volume * m.fs.costing.electricity_cost,
            to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
        ) * m.fs.costing.utilization_factor
    ) / m.fs.costing.annual_methane_production

    m.fs.costing.LCOM_comp["heat"] = (
        pyunits.convert(
            m.fs.metab_methane.heat[0] * m.fs.costing.heat_cost,
            to_units=m.fs.costing.base_currency / m.fs.costing.base_period,
        ) * m.fs.costing.utilization_factor
    ) / m.fs.costing.annual_methane_production

    def rule_LCOW_comp(b, c):
        if c in ["hydrogen_product", "methane_product"]:
            return (m.fs.costing.aggregate_flow_costs[c] *
                    m.fs.costing.utilization_factor /
                    m.fs.costing.annual_water_production)
        else:
            return (m.fs.costing.LCOH_comp[c] *
                    m.fs.costing.annual_hydrogen_production +
                    m.fs.costing.LCOM_comp[c] *
                    m.fs.costing.annual_methane_production
                    ) / m.fs.costing.annual_water_production

    m.fs.costing.LCOW_comp = Expression(m.fs.costing.LC_comp,
                                        rule=rule_LCOW_comp)

    def rule_LCOCR_comp(b, c):
        if c in ["hydrogen_product", "methane_product"]:
            return (m.fs.costing.aggregate_flow_costs[c] *
                    m.fs.costing.utilization_factor /
                    m.fs.costing.annual_cod_removal)
        else:
            return (m.fs.costing.LCOH_comp[c] *
                    m.fs.costing.annual_hydrogen_production +
                    m.fs.costing.LCOM_comp[c] *
                    m.fs.costing.annual_methane_production
                    ) / m.fs.costing.annual_cod_removal

    m.fs.costing.LCOCR_comp = Expression(m.fs.costing.LC_comp,
                                         rule=rule_LCOCR_comp)