File size: 3,214 Bytes
0c01b91
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2b18376
 
 
0c01b91
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
845f221
 
 
 
 
 
65c549b
845f221
0c01b91
 
 
845f221
0c01b91
 
845f221
 
 
3ac01c4
845f221
0c01b91
 
 
 
 
 
 
 
 
 
 
4b0d0e9
 
eece087
5a7e9ca
 
 
 
 
eece087
5a7e9ca
 
 
 
 
 
eece087
5a7e9ca
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
# Everything here goes into the app.py file
# Define Gradio inference function

# 15 March 2025
# Prakash Kota
# East Greenbush

import numpy as np
import tensorflow as tf
import os
import gradio as gr
import joblib

# Fixed reactor parameters
V = 100   # Reactor volume (L)
k = 0.1   # Reaction rate constant (1/min)
delta_H = -50000  # Heat of reaction (J/mol)
rho = 1   # Density in kg/L
Cp = 4184  # Heat capacity in J/kg·K

# Define the model directory
model_dir = "./model"

# Define Gradio inference function
def predict_cstr(CA_in, T_in, F):
    # Load scalers and model
    scaler_X = joblib.load(f"{model_dir}/scaler_X.pkl")
    scaler_Y = joblib.load(f"{model_dir}/scaler_Y.pkl")
    model = tf.keras.models.load_model(f"{model_dir}/cstr_model.keras")
    
    # Scale input
    input_scaled = scaler_X.transform([[CA_in, T_in, F]])
    
    # Predict using the model
    prediction_scaled = model.predict(input_scaled)
    prediction_original = scaler_Y.inverse_transform(prediction_scaled)
    CA_ss_pred, T_ss_pred = prediction_original[0]
    
    # Compute analytical solution
    CA_ss_analytical = (CA_in * (F / V)) / ((F / V) + k)
    T_ss_analytical = T_in + ((-delta_H * k * CA_ss_analytical) / (rho * Cp)) * (V / F)
    
    # Compute % Error and % Accuracy for Concentration
    #percent_error_CA = abs((CA_ss_pred - CA_ss_analytical) / CA_ss_analytical) * 100
    percent_accuracy_CA = (1 - abs(CA_ss_pred - CA_ss_analytical) / CA_ss_analytical) * 100

    # Compute % Error and % Accuracy for Temperature
    #percent_error_T = abs((T_ss_pred - T_ss_analytical) / T_ss_analytical) * 100
    percent_accuracy_T = (1 - abs(T_ss_pred - T_ss_analytical) / T_ss_analytical) * 100

    
    return (f"Predicted CA_ss: {CA_ss_pred:.4f} mol/L\n"
            f"Predicted T_ss: {T_ss_pred:.2f} K\n"
            f"\n"
            f"Analytical CA_ss: {CA_ss_analytical:.4f} mol/L\n"
            f"Analytical T_ss: {T_ss_analytical:.2f} K\n"
            f"\n"
            f"Accuracy\n"
            f"% Concentration Accuracy: {percent_accuracy_CA:.2f}%\n"
            f"% Temperature Accuracy: {percent_accuracy_T:.2f}%\n")


# Deploy using Gradio
iface = gr.Interface(
    fn=predict_cstr,
    inputs=[
        gr.Number(label="Input Concentration CA_in - Range [0.5-2.0] mol/L"),
        gr.Number(label="Input Temperature T_in - Range [300-350] K"),
        gr.Number(label="CSTR Flow Rate F - Range [5-20] L/min")
    ],
    outputs="text",
    title="CSTR Surrogate Model Inference",
    description="Enter the input values to predict steady-state concentration and temperature."
)    

# Add the Markdown footer with a clickable hyperlink
footer = gr.Markdown(
    'For details about the model, please see the article - '
    '[Bringing Historical Process Data to Life: Unlocking AI’s Goldmine with Neural Networks for Smarter Manufacturing](https://prakashkota.com/2025/03/16/bringing-historical-process-data-to-life-unlocking-ais-goldmine-with-neural-networks-for-smarter-manufacturing/)'
)

# Launch the interface with the footer
with gr.Blocks() as demo:
    iface.render()
    footer.render()

# Ensure the app launches when executed
if __name__ == "__main__":
    demo.launch(share=True)