smonizzzz commited on
Commit
45b395d
·
verified ·
1 Parent(s): c4e3330

Upload main.py with huggingface_hub

Browse files
Files changed (1) hide show
  1. main.py +118 -0
main.py ADDED
@@ -0,0 +1,118 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ """
2
+ Pipeline Deep Learning — Análise de Escoliose (regressão de ângulos de Cobb)
3
+
4
+ Uso (treino):
5
+ python main.py --mode train --data_root ./data --epochs 100
6
+
7
+ Uso (teste):
8
+ python main.py --mode test --data_root ./data --ckpt results/scoliosis_hrnet/best.pth
9
+
10
+ Uso (inferência numa imagem):
11
+ python main.py --mode infer --image rx.jpg --ckpt results/scoliosis_hrnet/best.pth
12
+ """
13
+
14
+ import argparse
15
+ import json
16
+ import sys
17
+ from pathlib import Path
18
+
19
+ import torch
20
+ import cv2
21
+ import albumentations as A
22
+ from albumentations.pytorch import ToTensorV2
23
+
24
+ sys.path.insert(0, str(Path(__file__).parent))
25
+
26
+ from data.dataset import build_dataloaders, IMAGE_SIZE
27
+ from models.hrnet import build_model
28
+ from train import train, evaluate_test, DEFAULT_CONFIG
29
+
30
+
31
+ def severity(angle):
32
+ if angle < 10: return "Normal"
33
+ if angle < 25: return "Leve"
34
+ if angle < 40: return "Moderada"
35
+ return "Grave"
36
+
37
+
38
+ @torch.no_grad()
39
+ def infer_single_image(image_path, ckpt_path, arch="hrnet", show=False):
40
+ device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
41
+
42
+ model = build_model(arch=arch, num_outputs=3)
43
+ ckpt = torch.load(ckpt_path, map_location=device)
44
+ model.load_state_dict(ckpt["model"])
45
+ model = model.to(device).eval()
46
+
47
+ img = cv2.imread(image_path, cv2.IMREAD_GRAYSCALE)
48
+ assert img is not None, f"Não foi possível ler: {image_path}"
49
+ img = cv2.cvtColor(img, cv2.COLOR_GRAY2RGB)
50
+
51
+ transform = A.Compose([
52
+ A.CLAHE(clip_limit=3.0, p=1.0),
53
+ A.Resize(IMAGE_SIZE, IMAGE_SIZE),
54
+ A.Normalize(mean=(0.485, 0.456, 0.406), std=(0.229, 0.224, 0.225)),
55
+ ToTensorV2(),
56
+ ])
57
+ tensor = transform(image=img)["image"].unsqueeze(0).to(device)
58
+
59
+ angles = model(tensor)[0].cpu().tolist()
60
+ labels = ["Torácico proximal", "Torácico principal", "Lombar"]
61
+
62
+ print("\n── Ângulos de Cobb ──")
63
+ for label, angle in zip(labels, angles):
64
+ print(f" {label}: {angle:.1f}° — {severity(angle)}")
65
+
66
+ return angles
67
+
68
+
69
+ def parse_args():
70
+ p = argparse.ArgumentParser()
71
+ p.add_argument("--mode", choices=["train", "test", "infer"], default="train")
72
+ p.add_argument("--data_root", type=str, default="./data")
73
+ p.add_argument("--arch", type=str, default="hrnet")
74
+ p.add_argument("--epochs", type=int, default=100)
75
+ p.add_argument("--batch", type=int, default=8)
76
+ p.add_argument("--lr", type=float, default=1e-3)
77
+ p.add_argument("--image", type=str, default=None)
78
+ p.add_argument("--ckpt", type=str, default=None)
79
+ p.add_argument("--exp_name", type=str, default="scoliosis_hrnet")
80
+ p.add_argument("--resume", type=str, default=None)
81
+ p.add_argument("--show", action="store_true")
82
+ return p.parse_args()
83
+
84
+
85
+ def main():
86
+ args = parse_args()
87
+ cfg = {**DEFAULT_CONFIG,
88
+ "arch": args.arch, "epochs": args.epochs,
89
+ "batch_size": args.batch, "lr": args.lr,
90
+ "exp_name": args.exp_name}
91
+
92
+ if args.mode == "train":
93
+ print(f"\n== Modo: TREINO | {args.epochs} epochs ==")
94
+ train_loader, val_loader, test_loader = build_dataloaders(
95
+ args.data_root, cfg["batch_size"], cfg["num_workers"])
96
+ model = build_model(arch=cfg["arch"], num_outputs=cfg["num_outputs"])
97
+ history = train(model, train_loader, val_loader, cfg, resume_ckpt=args.resume)
98
+ best = str(Path(cfg["output_dir"]) / cfg["exp_name"] / "best.pth")
99
+ evaluate_test(model, test_loader, cfg, ckpt_path=best)
100
+
101
+ elif args.mode == "test":
102
+ assert args.ckpt, "Forneça --ckpt"
103
+ _, _, test_loader = build_dataloaders(
104
+ args.data_root, cfg["batch_size"], cfg["num_workers"])
105
+ model = build_model(arch=cfg["arch"], num_outputs=cfg["num_outputs"])
106
+ results = evaluate_test(model, test_loader, cfg, ckpt_path=args.ckpt)
107
+ out = Path(cfg["output_dir"]) / cfg["exp_name"] / "test_results.json"
108
+ out.parent.mkdir(parents=True, exist_ok=True)
109
+ with open(out, "w") as f:
110
+ json.dump(results, f, indent=2)
111
+
112
+ elif args.mode == "infer":
113
+ assert args.image and args.ckpt, "Forneça --image e --ckpt"
114
+ infer_single_image(args.image, args.ckpt, args.arch, args.show)
115
+
116
+
117
+ if __name__ == "__main__":
118
+ main()