Marcel0123 commited on
Commit
15de49c
Β·
verified Β·
1 Parent(s): 5217123

Upload 3 files

Browse files
Files changed (2) hide show
  1. README.md +5 -7
  2. app.py +24 -37
README.md CHANGED
@@ -1,10 +1,8 @@
1
- # Live Supervised Learning (Linear Regression) β€” with Loss Curve
2
 
3
- Gradio-app die in real-time laat zien hoe een lineaire regressie leert op een 2D-dataset.
4
- Deze versie toont **twee live plots**: (1) data + regressielijn en (2) **loss curve (MSE per epoch)**.
5
- De app start automatisch met trainen bij het openen (geen uploads nodig).
6
 
7
- ## Lokaal draaien
8
  ```bash
9
  pip install -r requirements.txt
10
  python app.py
@@ -12,5 +10,5 @@ python app.py
12
 
13
  ## Deploy naar Hugging Face Spaces
14
  1. Maak een nieuwe Space aan β†’ **Gradio** template.
15
- 2. Upload `app.py`, `requirements.txt` en `README.md` (of upload het zip-bestand en pak het uit).
16
- 3. Start de Space. De app begint automatisch met trainen met de standaardwaarden.
 
1
+ # Live Supervised Learning (Linear Regression)
2
 
3
+ Een Gradio-app die in real-time laat zien hoe een lineaire regressie leert op een 2D-dataset.
 
 
4
 
5
+ ## Run lokaal
6
  ```bash
7
  pip install -r requirements.txt
8
  python app.py
 
10
 
11
  ## Deploy naar Hugging Face Spaces
12
  1. Maak een nieuwe Space aan β†’ **Gradio** template.
13
+ 2. Upload `app.py`, `requirements.txt` en `README.md`.
14
+ 3. Wacht tot de Space bouwt en start.
app.py CHANGED
@@ -17,14 +17,14 @@ def load_dataset(name: str, n_samples: int = 200, noise: float = 10.0):
17
  return X, y, "Synthetische data (y = 4x - 2 + noise)"
18
  elif name == "Diabetes (BMI vs target)":
19
  d = datasets.load_diabetes()
20
- X = d.data[:, 2] # BMI feature
21
  y = d.target
22
  return X, y, "Diabetes: BMI vs. disease progression"
23
  elif name == "California Housing (MedInc vs value)":
24
  try:
25
  ch = datasets.fetch_california_housing()
26
- X = ch.data[:, 0] # MedInc
27
- y = ch.target # MedHouseValue
28
  return X, y, "California Housing: MedInc vs. house value"
29
  except Exception:
30
  X, y, _ = load_dataset("Synthetisch", n_samples=n_samples, noise=noise)
@@ -32,47 +32,40 @@ def load_dataset(name: str, n_samples: int = 200, noise: float = 10.0):
32
  else:
33
  raise ValueError("Onbekende dataset")
34
 
 
35
  # ------------------------------
36
- # Training (SGD) voor y = w*x + b met real-time visualisatie
37
  # ------------------------------
38
  def sgd_train_generator(dataset_name, lr, epochs, batch_size, n_samples, noise, seed):
39
  rng = np.random.RandomState(int(seed))
40
  x, y, label = load_dataset(dataset_name, n_samples=n_samples, noise=noise)
41
-
42
  n = x.shape[0]
43
  x = x.astype(np.float64)
44
  y = y.astype(np.float64)
45
 
46
- w = 0.0
47
- b = 0.0
48
-
49
  x_min, x_max = float(np.min(x)), float(np.max(x))
50
- losses = []
51
 
52
  for epoch in range(1, int(epochs) + 1):
53
  x, y = shuffle(x, y, random_state=rng)
54
-
55
  for start in range(0, n, int(batch_size)):
56
  end = min(start + int(batch_size), n)
57
- xb = x[start:end]
58
- yb = y[start:end]
59
-
60
  yhat = w * xb + b
61
  err = yb - yhat
62
  dw = -(2.0 / xb.size) * np.sum(xb * err)
63
  db = -(2.0 / xb.size) * np.sum(err)
64
-
65
  w -= lr * dw
66
  b -= lr * db
67
 
68
- # Volledige-set MSE
69
  y_pred = w * x + b
70
  mse = float(np.mean((y - y_pred) ** 2))
71
- losses.append(mse)
72
 
73
- # Plot 1: data + regressielijn
74
- fig_main = plt.figure(figsize=(6, 4))
75
- ax1 = fig_main.add_subplot(111)
76
  ax1.scatter(x, y, alpha=0.6, s=18)
77
  xs = np.linspace(x_min, x_max, 200)
78
  ax1.plot(xs, w * xs + b, linewidth=2)
@@ -82,24 +75,25 @@ def sgd_train_generator(dataset_name, lr, epochs, batch_size, n_samples, noise,
82
  ax1.grid(True, linestyle=":", linewidth=0.6)
83
  plt.tight_layout()
84
 
85
- # Plot 2: loss-curve
86
- fig_loss = plt.figure(figsize=(6, 3))
87
- ax2 = fig_loss.add_subplot(111)
88
- ax2.plot(range(1, len(losses)+1), losses, marker="o", linewidth=1.5)
89
- ax2.set_title("Loss (MSE) per epoch")
90
  ax2.set_xlabel("Epoch")
91
  ax2.set_ylabel("MSE")
92
  ax2.grid(True, linestyle=":", linewidth=0.6)
93
  plt.tight_layout()
94
 
95
- yield fig_main, fig_loss, f"w = {w:.4f}, b = {b:.4f}, MSE = {mse:.4f}"
 
96
 
97
  # ------------------------------
98
  # Uitlegtekst
99
  # ------------------------------
100
  THEORY_MD = r"""
101
  ### Wat is supervised learning?
102
- Bij **supervised learning** leer je een model aan de hand van voorbeeldparen (input -> gewenste output). Het doel is een functie te vinden die de relatie tussen input en output goed benadert.
103
 
104
  ### Lineaire regressie in 1D
105
  We passen een lijn \( y = w x + b \) aan op data. We minimaliseren de **Mean Squared Error (MSE)**:
@@ -107,6 +101,7 @@ We passen een lijn \( y = w x + b \) aan op data. We minimaliseren de **Mean Squ
107
  We gebruiken **stochastic gradient descent (SGD)** om \(w\) en \(b\) stapje voor stapje te verbeteren.
108
  """
109
 
 
110
  # ------------------------------
111
  # Gradio UI
112
  # ------------------------------
@@ -131,22 +126,14 @@ with gr.Blocks(title="Live Supervised Learning: Linear Regression") as demo:
131
  seed = gr.Slider(0, 9999, value=42, step=1, label="Random seed")
132
  train_btn = gr.Button("Train live")
133
  with gr.Column(scale=2):
134
- plot_main = gr.Plot(label="Data & regressielijn (live)")
135
- plot_loss = gr.Plot(label="Loss-curve (MSE per epoch)")
136
  metrics = gr.Markdown()
137
 
138
- # Knoop de generator aan de UI
139
  train_btn.click(
140
  fn=sgd_train_generator,
141
  inputs=[dataset, lr, epochs, batch, n_samples, noise, seed],
142
- outputs=[plot_main, plot_loss, metrics]
143
- )
144
-
145
- # Auto-train bij het openen
146
- demo.load(
147
- fn=sgd_train_generator,
148
- inputs=[dataset, lr, epochs, batch, n_samples, noise, seed],
149
- outputs=[plot_main, plot_loss, metrics]
150
  )
151
 
152
  if __name__ == "__main__":
 
17
  return X, y, "Synthetische data (y = 4x - 2 + noise)"
18
  elif name == "Diabetes (BMI vs target)":
19
  d = datasets.load_diabetes()
20
+ X = d.data[:, 2]
21
  y = d.target
22
  return X, y, "Diabetes: BMI vs. disease progression"
23
  elif name == "California Housing (MedInc vs value)":
24
  try:
25
  ch = datasets.fetch_california_housing()
26
+ X = ch.data[:, 0]
27
+ y = ch.target
28
  return X, y, "California Housing: MedInc vs. house value"
29
  except Exception:
30
  X, y, _ = load_dataset("Synthetisch", n_samples=n_samples, noise=noise)
 
32
  else:
33
  raise ValueError("Onbekende dataset")
34
 
35
+
36
  # ------------------------------
37
+ # Training (SGD) met live plots
38
  # ------------------------------
39
  def sgd_train_generator(dataset_name, lr, epochs, batch_size, n_samples, noise, seed):
40
  rng = np.random.RandomState(int(seed))
41
  x, y, label = load_dataset(dataset_name, n_samples=n_samples, noise=noise)
 
42
  n = x.shape[0]
43
  x = x.astype(np.float64)
44
  y = y.astype(np.float64)
45
 
46
+ w, b = 0.0, 0.0
 
 
47
  x_min, x_max = float(np.min(x)), float(np.max(x))
48
+ loss_history = []
49
 
50
  for epoch in range(1, int(epochs) + 1):
51
  x, y = shuffle(x, y, random_state=rng)
 
52
  for start in range(0, n, int(batch_size)):
53
  end = min(start + int(batch_size), n)
54
+ xb, yb = x[start:end], y[start:end]
 
 
55
  yhat = w * xb + b
56
  err = yb - yhat
57
  dw = -(2.0 / xb.size) * np.sum(xb * err)
58
  db = -(2.0 / xb.size) * np.sum(err)
 
59
  w -= lr * dw
60
  b -= lr * db
61
 
 
62
  y_pred = w * x + b
63
  mse = float(np.mean((y - y_pred) ** 2))
64
+ loss_history.append(mse)
65
 
66
+ # Plot scatter + regressielijn
67
+ fig1 = plt.figure(figsize=(6, 4))
68
+ ax1 = fig1.add_subplot(111)
69
  ax1.scatter(x, y, alpha=0.6, s=18)
70
  xs = np.linspace(x_min, x_max, 200)
71
  ax1.plot(xs, w * xs + b, linewidth=2)
 
75
  ax1.grid(True, linestyle=":", linewidth=0.6)
76
  plt.tight_layout()
77
 
78
+ # Plot loss curve
79
+ fig2 = plt.figure(figsize=(6, 4))
80
+ ax2 = fig2.add_subplot(111)
81
+ ax2.plot(range(1, epoch + 1), loss_history, marker="o")
82
+ ax2.set_title("Loss curve (MSE per epoch)")
83
  ax2.set_xlabel("Epoch")
84
  ax2.set_ylabel("MSE")
85
  ax2.grid(True, linestyle=":", linewidth=0.6)
86
  plt.tight_layout()
87
 
88
+ yield fig1, fig2, f"w = {w:.4f}, b = {b:.4f}, MSE = {mse:.4f}"
89
+
90
 
91
  # ------------------------------
92
  # Uitlegtekst
93
  # ------------------------------
94
  THEORY_MD = r"""
95
  ### Wat is supervised learning?
96
+ Bij **supervised learning** leer je een model aan de hand van voorbeeldparen *(input β†’ gewenste output)*. Het doel is een functie te vinden die de relatie tussen input en output goed benadert.
97
 
98
  ### Lineaire regressie in 1D
99
  We passen een lijn \( y = w x + b \) aan op data. We minimaliseren de **Mean Squared Error (MSE)**:
 
101
  We gebruiken **stochastic gradient descent (SGD)** om \(w\) en \(b\) stapje voor stapje te verbeteren.
102
  """
103
 
104
+
105
  # ------------------------------
106
  # Gradio UI
107
  # ------------------------------
 
126
  seed = gr.Slider(0, 9999, value=42, step=1, label="Random seed")
127
  train_btn = gr.Button("Train live")
128
  with gr.Column(scale=2):
129
+ plot_data = gr.Plot(label="Data & regressielijn (live)")
130
+ plot_loss = gr.Plot(label="Loss curve (MSE)")
131
  metrics = gr.Markdown()
132
 
 
133
  train_btn.click(
134
  fn=sgd_train_generator,
135
  inputs=[dataset, lr, epochs, batch, n_samples, noise, seed],
136
+ outputs=[plot_data, plot_loss, metrics]
 
 
 
 
 
 
 
137
  )
138
 
139
  if __name__ == "__main__":