Skip to content

Latest commit

 

History

20 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 

Repository files navigation

CNN Based Automated Casting Defect Detection & Visualization System

Dataset Details

Casting manufacturing dataset of submersible pump impellers to automate defect detection. Contains 7,348 grayscale images (300×300px) with two classes OK and Defective addressing the industry's manual inspection bottleneck that causes financial losses and accuracy gaps. We split the dataset as (5,307), validation (1,326), and test (715) with augmentation. Classes: OK and Defective.

Quick Stats

Metric Value
Test Accuracy 94%
Defect Recall 100%
Defect Precision 92%
F1-Score 0.96
ROC-AUC 0.998
Model Size 495 KB

Setup & Installation

# Clone/download repository
cd casting-defect-detection

# Create virtual environment
python -m venv venv
source venv/bin/activate  # Windows: venv\Scripts\activate

# Install dependencies
pip install -r requirements.txt

Dataset & Training

Dataset: Kaggle Industrial Casting Product Dataset

  • Train: 5,307 images (80% of train folder)
  • Val: 1,326 images (20% of train folder)
  • Test: 715 images (completely unseen)
  • Classes: OK (262), Defective (453)
  • Resolution: 300×300 grayscale

Augmentation Applied:

  • Rotation (±20°), Horizontal/Vertical Flip
  • Zoom (0.15), Brightness (0.85-1.15)
  • Applied only to training set

Training: Open CastingCNN.ipynb and run cells sequentially.


Model Architecture

3-Block Convolutional Neural Network

Input (300×300×1)
    ↓
Block 1: Conv2D(32) → BatchNorm → MaxPool
    ↓
Block 2: Conv2D(64) → BatchNorm → MaxPool
    ↓
Block 3: Conv2D(128) → BatchNorm → MaxPool [GradCAM source]
    ↓
GlobalAveragePooling → Dense(256) → Dropout(0.5)
    ↓
Output: Sigmoid (binary classification)
  • Total Parameters: 126,849 (495 KB)
  • Optimizer: Adam (learning_rate=1.25e-05)
  • Loss: Binary CrossEntropy
  • Batch Size: 32

Results

Test Set Performance

              precision    recall  f1-score   support
          OK       1.00      0.85      0.92       262
   Defective       0.92      1.00      0.96       453
    accuracy                           0.94       715
weighted avg       0.95      0.94      0.94       715

Confusion Matrix

  • True Positives: 452/453 (99.8% catch rate)
  • True Negatives: 222/262 (85% acceptance)
  • False Negatives: 1 (defect escaped)
  • False Positives: 40 (good parts rejected)

Training History

Training curves showing smooth convergence over 25 epochs

Key Observations:

  • Training and validation curves move together (no overfitting)
  • Convergence at epoch 24
  • Loss decreases smoothly from 0.6 → 0.1
  • Validation accuracy reaches 98%

Usage

1. Single Image Inspection

from tensorflow.keras.models import load_model
import cv2
import numpy as np

# Load model
model = load_model('best_model.h5')

# Load and prepare image
img = cv2.imread('casting_image.png', cv2.IMREAD_GRAYSCALE)
img_array = cv2.resize(img, (300, 300)).astype(np.float32) / 255.0
img_input = np.expand_dims(img_array, axis=(0, -1))

# Predict
defect_prob = model.predict(img_input)[0][0]
is_defective = "Defective" if defect_prob > 0.5 else "OK"

print(f"Prediction: {is_defective}")
print(f"Confidence: {defect_prob*100:.2f}%")

Sample Output on Single Image

2. Batch Processing

from pathlib import Path
import pandas as pd

casting_dir = Path('castings/')
results = []

for img_path in casting_dir.glob('*.png'):
    img = cv2.imread(str(img_path), cv2.IMREAD_GRAYSCALE)
    img_array = cv2.resize(img, (300, 300)).astype(np.float32) / 255.0
    img_input = np.expand_dims(img_array, axis=(0, -1))
    
    defect_prob = model.predict(img_input)[0][0]
    results.append({
        'image': img_path.name,
        'defect_confidence': f"{defect_prob*100:.2f}%",
        'prediction': 'Defective' if defect_prob > 0.5 else 'OK'
    })

df = pd.DataFrame(results)
df.to_csv('inspection_results.csv', index=False)
print(df)

3. With GradCAM Visualization

import tensorflow as tf

def generate_gradcam(model, img_array, layer_name="block3_conv"):
    """Generate Grad-CAM heatmap"""
    last_conv_layer = model.get_layer(layer_name)
    grad_model = tf.keras.models.Model(
        [model.inputs],
        [last_conv_layer.output, model.output]
    )
    
    with tf.GradientTape() as tape:
        conv_outputs, predictions = grad_model(img_array)
        class_channel = predictions[:, 0]
    
    grads = tape.gradient(class_channel, conv_outputs)
    pooled_grads = tf.reduce_mean(grads, axis=(0, 1, 2))
    conv_outputs = conv_outputs[0]
    heatmap = conv_outputs @ pooled_grads[..., tf.newaxis]
    heatmap = tf.squeeze(heatmap)
    heatmap = tf.maximum(heatmap, 0) / tf.math.reduce_max(heatmap)
    
    return heatmap.numpy()

# Use it
heatmap = generate_gradcam(model, img_input)
# Visualize heatmap overlay on original image

GradCAM

GradCAM highlights which image regions influence the model's decision:

GradCAM visualization showing defect localization

How to interpret:

  • Red regions: High activation (important for decision)
  • Blue regions: Low activation (ignored by model)
  • Green/Yellow: Medium importance

This proves the model learns genuine defect patterns, not spurious features.


Prediction Distribution

Histogram of defect probabilities showing clear separation

Interpretation:

  • Two clear peaks: one at 0 (OK) and one at 1 (Defective)
  • Clean separation indicates strong model confidence
  • Decision threshold at 0.5 effectively separates classes

ROC Curve & Performance

ROC curve showing AUC=0.998 near-perfect discrimination

Why ROC-AUC = 0.998 is important:

  • Model separates defective from OK across all thresholds
  • Works perfectly even if you adjust decision threshold
  • Robust to different operating points
  • Better than threshold-dependent metrics alone

Severity Classification System

Model outputs mapped to 4 tier severity levels that are also changeable based on tolelrance during manufacturing

Tier Confidence Action
PASS < 50% Accept part
LOW 50-69% Monitor
MODERATE 70-89% Manual review
CRITICAL ≥ 90% Reject immediately
def assess_severity(defect_prob):
    if defect_prob < 0.5:
        return {'tier': 'PASS', 'action': 'Accept'}
    elif defect_prob < 0.7:
        return {'tier': 'LOW', 'action': 'Monitor'}
    elif defect_prob < 0.9:
        return {'tier': 'MODERATE', 'action': 'Manual Review'}
    else:
        return {'tier': 'CRITICAL', 'action': 'Reject'}

severity = assess_severity(0.95)
print(f"Severity: {severity['tier']}{severity['action']}")

File Structure


CNN-based-casting-defect-detection/
├── CastingCNN.ipynb          
├── best_model.h5             
├── requirements.txt          
├── README.md                
└── results      

Key Findings on our dataset

100% Defect Recall: Catches essentially all defects (only 1 missed out of 453)
92% Precision: When model rejects, 92% are truly defective
0.998 ROC-AUC: Near perfect class separation
Explainable: GradCAM shows exactly where model focuses


Manufacturing Implications

Out of 715 test castings:

✓ Correct: 674 (94%)
  ├─ 222 good parts accepted
  └─ 452 defects caught

✗ Errors: 41 (6%)
  ├─ 40 good parts rejected (15% false rejection)
  └─ 1 defect escaped (0.2% miss rate - acceptable)


To run - Use Kaggle generated API Key and your username (Import Dataset block in CNN.ipynb)

Requirements

See requirements.txt:

tensorflow>=2.10
numpy>=1.21
opencv-python>=4.5
matplotlib>=3.5
pandas>=1.3
scikit-learn>=1.0

Install with:

pip install -r requirements.txt

Course Project Manufacturing Engineering ME 222 IIT Guwahati

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages