buoyrina commited on
Commit
02dd72e
·
1 Parent(s): d0154da

consolidate

Browse files
Files changed (1) hide show
  1. app.py +239 -19
app.py CHANGED
@@ -59,27 +59,247 @@ def matrix_vector_multiplication_visualization(matrix, vector):
59
  except Exception as e:
60
  return f"Error: {str(e)}", None
61
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
62
  # Create the Gradio app
63
  with gr.Blocks() as app:
64
- gr.Markdown("## Matrix-Vector Multiplication Visualization")
65
- gr.Markdown("""
66
- - Enter a **2x2 matrix** as `a,b;c,d` (rows separated by semicolons).
67
- - Enter a **2D vector** as `x,y`.
68
- - See the original vector (red), transformed vector (blue), and grid transformation.
69
- """)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
70
 
71
- with gr.Row():
72
- matrix_input = gr.Textbox(label="Matrix (2x2, e.g., 1,0;0,1)", placeholder="e.g., 1,0;0,1")
73
- vector_input = gr.Textbox(label="Vector (2D, e.g., 1,1)", placeholder="e.g., 1,1")
74
-
75
- output_text = gr.Textbox(label="Result")
76
- output_image = gr.Image(label="Visualization")
77
-
78
- calculate_button = gr.Button("Visualize")
79
- calculate_button.click(
80
- fn=matrix_vector_multiplication_visualization,
81
- inputs=[matrix_input, vector_input],
82
- outputs=[output_text, output_image]
83
- )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
84
 
85
  app.launch()
 
59
  except Exception as e:
60
  return f"Error: {str(e)}", None
61
 
62
+ def visualize_points_and_vectors_with_start(points, vectors):
63
+ try:
64
+ # Parse points
65
+ points = [list(map(float, p.split(','))) for p in points.split(';') if p.strip()]
66
+
67
+ # Parse vectors with starting points
68
+ vectors_with_start = [
69
+ list(map(float, v.split(','))) for v in vectors.split(';') if v.strip()
70
+ ]
71
+
72
+ # Create the plot
73
+ fig, ax = plt.subplots(figsize=(6, 6))
74
+
75
+ # Plot points
76
+ for point in points:
77
+ ax.plot(point[0], point[1], 'o', label=f"Point ({point[0]}, {point[1]})")
78
+
79
+ # Plot vectors with starting points
80
+ for vector in vectors_with_start:
81
+ if len(vector) == 4: # Check format [start_x, start_y, vector_x, vector_y]
82
+ start_x, start_y, vec_x, vec_y = vector
83
+ ax.quiver(
84
+ start_x, start_y, vec_x, vec_y, angles='xy', scale_units='xy', scale=1,
85
+ color='r', label=f"Vector from ({start_x},{start_y}) to ({start_x+vec_x},{start_y+vec_y})"
86
+ )
87
+
88
+ # Plot settings
89
+ ax.axhline(0, color='black', linewidth=0.5)
90
+ ax.axvline(0, color='black', linewidth=0.5)
91
+ ax.set_xlim(-10, 10)
92
+ ax.set_ylim(-10, 10)
93
+ ax.set_aspect('equal')
94
+ ax.grid(True)
95
+ ax.legend()
96
+ ax.set_title("Points and Vectors Visualization")
97
+
98
+ # Save the plot to a BytesIO object
99
+ buf = BytesIO()
100
+ plt.savefig(buf, format='png')
101
+ buf.seek(0)
102
+ plt.close(fig)
103
+
104
+ return Image.open(buf)
105
+ except Exception as e:
106
+ return f"Error: {str(e)}"
107
+
108
+ def calculate_dot_product_and_angle(vector1, vector2):
109
+ try:
110
+ # Convert input strings to numpy arrays
111
+ vec1 = np.array([float(x) for x in vector1.split(",")])
112
+ vec2 = np.array([float(x) for x in vector2.split(",")])
113
+
114
+ # Check if vectors have the same length
115
+ if len(vec1) != len(vec2):
116
+ return "Error: Vectors must have the same length.", None
117
+
118
+ # Compute the dot product
119
+ dot_product = np.dot(vec1, vec2)
120
+
121
+ # Compute magnitudes of vectors
122
+ magnitude_vec1 = np.linalg.norm(vec1)
123
+ magnitude_vec2 = np.linalg.norm(vec2)
124
+
125
+ # Normalized dot product
126
+ normalized_dot_product = dot_product / (magnitude_vec1 * magnitude_vec2)
127
+
128
+ # Compute the angle in radians and convert to degrees
129
+ angle_radians = np.arccos(np.clip(normalized_dot_product, -1.0, 1.0))
130
+ angle_degrees = np.degrees(angle_radians)
131
+
132
+ explanation = (
133
+ f"Dot product: {dot_product}\n"
134
+ f"Normalized dot product: {normalized_dot_product:.4f}\n"
135
+ f"Angle (radians): {angle_radians:.4f}\n"
136
+ f"Angle (degrees): {angle_degrees:.4f}"
137
+ )
138
+
139
+ # Plot the vectors
140
+ fig, ax = plt.subplots(figsize=(6, 6))
141
+ ax.quiver(0, 0, vec1[0], vec1[1], angles='xy', scale_units='xy', scale=1, color='r', label="Vector 1")
142
+ ax.quiver(0, 0, vec2[0], vec2[1], angles='xy', scale_units='xy', scale=1, color='b', label="Vector 2")
143
+
144
+ # Plot settings
145
+ ax.set_xlim(-max(abs(vec1[0]), abs(vec2[0])) - 1, max(abs(vec1[0]), abs(vec2[0])) + 1)
146
+ ax.set_ylim(-max(abs(vec1[1]), abs(vec2[1])) - 1, max(abs(vec1[1]), abs(vec2[1])) + 1)
147
+ ax.axhline(0, color='black', linewidth=0.5)
148
+ ax.axvline(0, color='black', linewidth=0.5)
149
+ ax.set_aspect('equal')
150
+ ax.grid(True)
151
+ ax.legend()
152
+ ax.set_title("Vector Visualization")
153
+
154
+
155
+ # Save plot to a BytesIO object
156
+ buf = BytesIO()
157
+ plt.savefig(buf, format='png')
158
+ buf.seek(0)
159
+ plt.close(fig)
160
+
161
+ return explanation, Image.open(buf)
162
+ except ValueError:
163
+ return "Error: Please enter valid numeric values separated by commas.", None
164
+
165
+ def transformation_composition_with_vectors(matrix1, matrix2, vectors):
166
+ try:
167
+ # Parse input matrices
168
+ matrix1 = np.array([[float(x) for x in row.split(",")] for row in matrix1.split(";")])
169
+ matrix2 = np.array([[float(x) for x in row.split(",")] for row in matrix2.split(";")])
170
+
171
+ # Ensure both matrices are 2x2
172
+ if matrix1.shape != (2, 2) or matrix2.shape != (2, 2):
173
+ return "Error: Both matrices must be 2x2.", None
174
+
175
+ # Parse vectors
176
+ vectors = np.array([[float(x) for x in vector.split(",")] for vector in vectors.split(";")]).T
177
+ if vectors.shape[0] != 2:
178
+ return "Error: Vectors must be 2D (two components per vector).", None
179
+
180
+ # Compute the transformations
181
+ vectors_after_matrix1 = np.dot(matrix1, vectors)
182
+ vectors_after_composition = np.dot(np.dot(matrix2, matrix1), vectors)
183
+
184
+ # Plot the transformations
185
+ fig, ax = plt.subplots(figsize=(8, 8))
186
+
187
+ # Plot original vectors
188
+ for vector in vectors.T:
189
+ ax.quiver(0, 0, vector[0], vector[1], angles='xy', scale_units='xy', scale=1, color="gray", alpha=0.7)
190
+
191
+ # Plot vectors after Matrix 1
192
+ for vector in vectors_after_matrix1.T:
193
+ ax.quiver(0, 0, vector[0], vector[1], angles='xy', scale_units='xy', scale=1, color="orange", alpha=0.7)
194
+
195
+ # Plot vectors after composition
196
+ for vector in vectors_after_composition.T:
197
+ ax.quiver(0, 0, vector[0], vector[1], angles='xy', scale_units='xy', scale=1, color="blue", alpha=0.7)
198
+
199
+ # Add legend
200
+ ax.legend(["Original Vectors", "After Matrix 1", "After Matrix 2 × Matrix 1"], loc="upper left")
201
+
202
+ # Axes settings
203
+ ax.axhline(0, color="black", linewidth=0.5)
204
+ ax.axvline(0, color="black", linewidth=0.5)
205
+ ax.set_xlim(-3, 3)
206
+ ax.set_ylim(-3, 3)
207
+ ax.set_aspect("equal")
208
+ ax.grid(True)
209
+ ax.set_title("Matrix-Matrix Multiplication as Transformation Composition")
210
+
211
+ # Save the plot
212
+ buf = BytesIO()
213
+ plt.savefig(buf, format="png")
214
+ buf.seek(0)
215
+ plt.close(fig)
216
+
217
+ return "Success", Image.open(buf)
218
+ except Exception as e:
219
+ return f"Error: {str(e)}", None
220
  # Create the Gradio app
221
  with gr.Blocks() as app:
222
+ with gr.Tab("Points vs. Vectors"):
223
+ gr.Markdown("## Points and Vectors Visualization with Starting Points")
224
+ gr.Markdown("""
225
+ - **Points**: Enter semicolon-separated 2D points, e.g., `1,2; 3,4`.
226
+ - **Vectors**: Enter vectors with starting points in the format `start_x,start_y,vector_x,vector_y; ...`, e.g., `0,0,2,1; 3,4,-1,2`.
227
+ """)
228
+
229
+ with gr.Row():
230
+ points_input = gr.Textbox(label="Points (semicolon-separated)", placeholder="e.g., 1,2; 3,4")
231
+ vectors_input = gr.Textbox(label="Vectors (with starting points)", placeholder="e.g., 0,0,2,1; 3,4,-1,2")
232
+
233
+ output_image = gr.Image(label="Visualization")
234
+
235
+ visualize_button = gr.Button("Visualize")
236
+ visualize_button.click(
237
+ fn=visualize_points_and_vectors_with_start,
238
+ inputs=[points_input, vectors_input],
239
+ outputs=output_image
240
+ )
241
+ with gr.Tab("Vector Dot Product"):
242
+ gr.Markdown("## Dot Product, Normalized Dot Product, and Angle Calculator")
243
+ gr.Markdown("Enter two vectors (comma-separated) to calculate their dot product, normalized dot product, and angle.")
244
 
245
+ with gr.Row():
246
+ vector1_input = gr.Textbox(label="Vector 1", placeholder="e.g., 1, 2")
247
+ vector2_input = gr.Textbox(label="Vector 2", placeholder="e.g., 4, 5")
248
+
249
+ output_text = gr.Textbox(label="Result", lines=6)
250
+ output_image = gr.Image(label="Visualization")
251
+
252
+ calculate_button = gr.Button("Calculate and Visualize")
253
+ calculate_button.click(
254
+ fn=calculate_dot_product_and_angle,
255
+ inputs=[vector1_input, vector2_input],
256
+ outputs=[output_text, output_image]
257
+ )
258
+ with gr.Tab("Matrix-Vector Multiplication"):
259
+ gr.Markdown("## Matrix-Vector Multiplication Visualization")
260
+ gr.Markdown("""
261
+ - Enter a **2x2 matrix** as `a,b;c,d` (rows separated by semicolons).
262
+ - Enter a **2D vector** as `x,y`.
263
+ - See the original vector (red), transformed vector (blue), and grid transformation.
264
+ """)
265
+ with gr.Row():
266
+ matrix_input = gr.Textbox(label="Matrix (2x2, e.g., 1,0;0,1)", placeholder="e.g., 1,0;0,1")
267
+ vector_input = gr.Textbox(label="Vector (2D, e.g., 1,1)", placeholder="e.g., 1,1")
268
+
269
+ output_text = gr.Textbox(label="Result")
270
+ output_image = gr.Image(label="Visualization")
271
+
272
+ calculate_button = gr.Button("Visualize")
273
+ calculate_button.click(
274
+ fn=matrix_vector_multiplication_visualization,
275
+ inputs=[matrix_input, vector_input],
276
+ outputs=[output_text, output_image]
277
+ )
278
+
279
+ with gr.Tab('Matrix-Matrix Multiplication'):
280
+ gr.Markdown("## Matrix Multiplication as Transformation Composition (Using Vectors)")
281
+ gr.Markdown("""
282
+ - Enter two **2x2 matrices** in the format `a,b;c,d` (rows separated by semicolons).
283
+ - Enter vectors in the format `x1,y1;x2,y2;...` (semicolon-separated pairs).
284
+ - The app will show:
285
+ - The original vectors.
286
+ - The vectors after applying **Matrix 1**.
287
+ - The vectors after applying the composition (**Matrix 2 × Matrix 1**).
288
+ """)
289
+
290
+ with gr.Row():
291
+ matrix1_input = gr.Textbox(label="Matrix 1 (2x2, e.g., 1,0;0,1)", placeholder="e.g., 1,0;0,1")
292
+ matrix2_input = gr.Textbox(label="Matrix 2 (2x2, e.g., 2,0;0,1)", placeholder="e.g., 2,0;0,1")
293
+ vectors_input = gr.Textbox(label="Vectors (e.g., 1,0;0,1)", placeholder="e.g., 1,0;0,1")
294
+
295
+ output_text = gr.Textbox(label="Output")
296
+ output_image = gr.Image(label="Visualization")
297
+
298
+ calculate_button = gr.Button("Visualize")
299
+ calculate_button.click(
300
+ fn=transformation_composition_with_vectors,
301
+ inputs=[matrix1_input, matrix2_input, vectors_input],
302
+ outputs=[output_text, output_image]
303
+ )
304
 
305
  app.launch()