From a8cd638f9e98267a9530171a8c4e9c89d3611b08 Mon Sep 17 00:00:00 2001
From: renchao_lu <renchao.lu@gmail.com>
Date: Tue, 4 Jun 2019 18:11:15 +0200
Subject: [PATCH] [CL] Create class Output.

---
 ChemistryLib/CreateOutput.cpp |  59 ++++++++++++++++++++
 ChemistryLib/CreateOutput.h   |  26 +++++++++
 ChemistryLib/Output.h         | 100 ++++++++++++++++++++++++++++++++++
 3 files changed, 185 insertions(+)
 create mode 100644 ChemistryLib/CreateOutput.cpp
 create mode 100644 ChemistryLib/CreateOutput.h
 create mode 100644 ChemistryLib/Output.h

diff --git a/ChemistryLib/CreateOutput.cpp b/ChemistryLib/CreateOutput.cpp
new file mode 100644
index 00000000000..e0678dd1c48
--- /dev/null
+++ b/ChemistryLib/CreateOutput.cpp
@@ -0,0 +1,59 @@
+/**
+ * \copyright
+ * Copyright (c) 2012-2019, OpenGeoSys Community (http://www.opengeosys.org)
+ *            Distributed under a Modified BSD License.
+ *              See accompanying file LICENSE.txt or
+ *              http://www.opengeosys.org/project/license
+ *
+ */
+
+#include <numeric>
+#include "CreateOutput.h"
+
+namespace ChemistryLib
+{
+std::unique_ptr<Output> createOutput(
+    std::vector<Component> const& components,
+    std::vector<EquilibriumPhase> const& equilibrium_phases,
+    std::vector<KineticReactant> const& kinetic_reactants,
+    std::string const& project_file_name)
+{
+    // Mark which phreeqc output items will be held.
+    std::vector<OutputItem> accepted_items{{"pH", ItemType::pH},
+                                           {"pe", ItemType::pe}};
+    for (auto const& component : components)
+        accepted_items.emplace_back(component.name, ItemType::Component);
+    for (auto const& equilibrium_phase : equilibrium_phases)
+        accepted_items.emplace_back(equilibrium_phase.name,
+                                    ItemType::EquilibriumPhase);
+    for (auto const& kinetic_reactant : kinetic_reactants)
+        accepted_items.emplace_back(kinetic_reactant.name,
+                                    ItemType::KineticReactant);
+
+    // Record ids of which phreeqc output items will be dropped.
+    BasicOutputSetups basic_output_setups(project_file_name);
+    auto const num_dropped_basic_items =
+        basic_output_setups.getNumberOfDroppedItems();
+    std::vector<int> dropped_item_ids(num_dropped_basic_items);
+    std::iota(dropped_item_ids.begin(), dropped_item_ids.end(), 0);
+
+    auto const num_dvalue_equilibrium_phases = equilibrium_phases.size();
+    auto const num_dvalue_kinetic_reactants = kinetic_reactants.size();
+    int const num_dvalue_items =
+        num_dvalue_equilibrium_phases + num_dvalue_kinetic_reactants;
+
+    auto const num_basic_items =
+        basic_output_setups.getNumberOfItemsInDisplay();
+    auto const num_components = components.size();
+    auto dvalue_item_id = num_basic_items + num_components + 1;
+    for (int i = 0; i < num_dvalue_items; ++i)
+    {
+        dropped_item_ids.push_back(dvalue_item_id);
+        dvalue_item_id += 2 * (i + 1);
+    }
+
+    return std::make_unique<Output>(basic_output_setups,
+                                    std::move(accepted_items),
+                                    std::move(dropped_item_ids));
+}
+}  // namespace ChemistryLib
diff --git a/ChemistryLib/CreateOutput.h b/ChemistryLib/CreateOutput.h
new file mode 100644
index 00000000000..ae52db8b42a
--- /dev/null
+++ b/ChemistryLib/CreateOutput.h
@@ -0,0 +1,26 @@
+/**
+ * \copyright
+ * Copyright (c) 2012-2019, OpenGeoSys Community (http://www.opengeosys.org)
+ *            Distributed under a Modified BSD License.
+ *              See accompanying file LICENSE.txt or
+ *              http://www.opengeosys.org/project/license
+ *
+ */
+
+#pragma once
+
+#include <memory>
+
+#include "Output.h"
+#include "PhreeqcIOData/AqueousSolution.h"
+#include "PhreeqcIOData/EquilibriumPhase.h"
+#include "PhreeqcIOData/KineticReactant.h"
+
+namespace ChemistryLib
+{
+std::unique_ptr<Output> createOutput(
+    std::vector<Component> const& components,
+    std::vector<EquilibriumPhase> const& equilibrium_phases,
+    std::vector<KineticReactant> const& kinetic_reactants,
+    std::string const& project_file_name);
+}  // namespace ChemistryLib
diff --git a/ChemistryLib/Output.h b/ChemistryLib/Output.h
new file mode 100644
index 00000000000..8c947702d7e
--- /dev/null
+++ b/ChemistryLib/Output.h
@@ -0,0 +1,100 @@
+/**
+ * \copyright
+ * Copyright (c) 2012-2019, OpenGeoSys Community (http://www.opengeosys.org)
+ *            Distributed under a Modified BSD License.
+ *              See accompanying file LICENSE.txt or
+ *              http://www.opengeosys.org/project/license
+ *
+ */
+
+#pragma once
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+namespace ChemistryLib
+{
+class BasicOutputSetups
+{
+public:
+    BasicOutputSetups(std::string const& project_file_name)
+        : output_file(project_file_name + "_phreeqc.out")
+    {
+    }
+
+    int getNumberOfItemsInDisplay()
+    {
+        return display_simulation_id + display_state + display_solution_id +
+               display_distance + display_current_time + display_time_step +
+               display_pH + display_pe;
+    }
+
+    int getNumberOfDroppedItems()
+    {
+        return display_simulation_id + display_state + display_solution_id +
+               display_distance + display_current_time + display_time_step;
+    }
+
+    std::string const output_file;
+
+private:
+    static const bool display_simulation_id = false;
+    static const bool display_state = true;
+    static const bool display_solution_id = true;
+    static const bool display_distance = false;
+    static const bool display_current_time = false;
+    static const bool display_time_step = false;
+    static const bool display_pH = true;
+    static const bool display_pe = true;
+    static const bool use_high_precision = true;
+};
+
+enum class ItemType
+{
+    pH,
+    pe,
+    Component,
+    EquilibriumPhase,
+    KineticReactant
+};
+
+struct OutputItem
+{
+    OutputItem(std::string name_, ItemType item_type_)
+        : name(std::move(name_)), item_type(item_type_)
+    {
+    }
+
+    std::string const name;
+    ItemType const item_type;
+};
+
+struct Output
+{
+    Output(BasicOutputSetups basic_output_setups_,
+           std::vector<OutputItem>&& accepted_items_,
+           std::vector<int>&& dropped_item_ids_)
+        : basic_output_setups(basic_output_setups_),
+          accepted_items(std::move(accepted_items_)),
+          dropped_item_ids(std::move(dropped_item_ids_))
+    {
+    }
+
+    std::vector<OutputItem> getOutputItemsByItemType(ItemType item_type) const
+    {
+        std::vector<OutputItem> matching_items;
+        std::copy_if(accepted_items.cbegin(),
+                     accepted_items.cend(),
+                     std::back_inserter(matching_items),
+                     [&item_type](OutputItem const& accepted_item) {
+                         return accepted_item.item_type == item_type;
+                     });
+        return matching_items;
+    }
+
+    BasicOutputSetups const basic_output_setups;
+    std::vector<OutputItem> const accepted_items;
+    std::vector<int> const dropped_item_ids;
+};
+}  // namespace ChemistryLib
-- 
GitLab