VJBharathkumar commited on
Commit
c237f7a
·
verified ·
1 Parent(s): da1d399

Update src/streamlit_app.py

Browse files
Files changed (1) hide show
  1. src/streamlit_app.py +0 -119
src/streamlit_app.py CHANGED
@@ -112,125 +112,6 @@ def predict_prob(x: np.ndarray) -> float:
112
  prob = float(np.ravel(pred)[0])
113
  return max(0.0, min(1.0, prob))
114
 
115
- # -----------------------------
116
-
117
- # -----------------------------
118
- # -----------------------------
119
- # Grad-CAM (robust for nested ResNet backbone)
120
- # -----------------------------
121
- @st.cache_resource
122
- def get_backbone_and_last_conv():
123
- backbone_name = "resnet50" # your model has this layer name
124
- backbone = model.get_layer(backbone_name)
125
-
126
- last_conv = None
127
- for lyr in reversed(backbone.layers):
128
- if isinstance(lyr, tf.keras.layers.Conv2D):
129
- last_conv = lyr.name
130
- break
131
-
132
- if last_conv is None:
133
- raise ValueError("No Conv2D layer found inside resnet50 backbone.")
134
-
135
- # model that outputs the conv feature map
136
- conv_model = keras.Model(
137
- inputs=model.inputs,
138
- outputs=backbone.get_layer(last_conv).output
139
- )
140
-
141
- return backbone_name, last_conv, conv_model
142
-
143
- def make_gradcam_heatmap(img_batch: np.ndarray) -> np.ndarray:
144
- _, last_conv, conv_model = get_backbone_and_last_conv()
145
-
146
- x = tf.convert_to_tensor(img_batch, dtype=tf.float32)
147
-
148
- with tf.GradientTape() as tape:
149
- conv_out = conv_model(x, training=False) # (1, h, w, ch)
150
-
151
- preds = model(x, training=False)
152
- if isinstance(preds, (list, tuple)):
153
- prob = preds[-1]
154
- else:
155
- prob = preds
156
-
157
- loss = prob[:, 0] # binary prob
158
-
159
- grads = tape.gradient(loss, conv_out)
160
- if grads is None:
161
- raise ValueError(
162
- f"Gradients are None (cannot compute Grad-CAM). Last conv was: {last_conv}"
163
- )
164
-
165
- pooled_grads = tf.reduce_mean(grads, axis=(0, 1, 2))
166
- conv_out = conv_out[0]
167
-
168
- heatmap = tf.reduce_sum(conv_out * pooled_grads, axis=-1)
169
- heatmap = tf.maximum(heatmap, 0.0)
170
-
171
- denom = tf.reduce_max(heatmap) + 1e-8
172
- heatmap = heatmap / denom
173
-
174
- return heatmap.numpy()
175
-
176
-
177
- # -----------------------------
178
- # PDF generation (fix unicode issues)
179
- # -----------------------------
180
- # -----------------------------
181
- # PDF generator (robust wrapping)
182
- # -----------------------------
183
- def safe_text(s: str, max_len: int = 220) -> str:
184
- if s is None:
185
- return ""
186
- s = str(s)
187
-
188
- # replace unicode dashes/quotes
189
- s = s.replace("–", "-").replace("—", "-").replace("’", "'").replace("“", '"').replace("”", '"')
190
-
191
- # add break opportunities for long tokens (UUIDs, filenames)
192
- s = s.replace("-", "- ").replace("_", "_ ").replace("/", "/ ")
193
-
194
- # latin-1 safe
195
- s = s.encode("latin-1", "replace").decode("latin-1")
196
-
197
- # trim
198
- if len(s) > max_len:
199
- s = s[:max_len] + "..."
200
- return s
201
-
202
- def build_pdf_report(df_ok: pd.DataFrame, threshold: float, model_version: str) -> bytes:
203
- pdf = FPDF()
204
- pdf.set_auto_page_break(auto=True, margin=12)
205
- pdf.add_page()
206
-
207
- pdf.set_font("Helvetica", size=12)
208
-
209
- # effective width (prevents “not enough horizontal space”)
210
- w = pdf.w - pdf.l_margin - pdf.r_margin
211
-
212
- pdf.cell(0, 8, safe_text("Pneumonia Detection Report"), ln=True)
213
- pdf.set_font("Helvetica", size=10)
214
- pdf.cell(0, 6, safe_text(f"Generated: {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}"), ln=True)
215
- pdf.cell(0, 6, safe_text(f"Model Version: {model_version}"), ln=True)
216
- pdf.cell(0, 6, safe_text(f"Decision Threshold: {threshold:.2f}"), ln=True)
217
- pdf.ln(4)
218
-
219
- for _, row in df_ok.iterrows():
220
- lines = [
221
- f"File: {row['file_name']}",
222
- f"Probability: {row['probability']*100:.2f}%",
223
- f"Confidence: {row['confidence_level']}",
224
- f"Prediction: {row['prediction']}",
225
- ]
226
- for line in lines:
227
- pdf.multi_cell(w, 6, safe_text(line))
228
- pdf.ln(2)
229
-
230
- out = pdf.output(dest="S")
231
- if isinstance(out, str):
232
- out = out.encode("latin-1", "ignore")
233
- return out
234
 
235
 
236
  # -----------------------------
 
112
  prob = float(np.ravel(pred)[0])
113
  return max(0.0, min(1.0, prob))
114
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
115
 
116
 
117
  # -----------------------------