Skip to content

Instantly share code, notes, and snippets.

@bennyistanto
Created July 2, 2024 07:18
Show Gist options
  • Save bennyistanto/961788a02821b8676e7421503d52e0ef to your computer and use it in GitHub Desktop.
Save bennyistanto/961788a02821b8676e7421503d52e0ef to your computer and use it in GitHub Desktop.
The moving window approach is used to balance the advantages of capturing both spatial and temporal variations in precipitation patterns

Moving Window illustration

You can paste the below code into an online Python compiler like https://python-fiddle.com/ and grab the result instantly.

This script will generate a plot that illustrates:

  1. This highlighting the spatial moving window on the top layer. The selected pixel at (4,5) will be red, and the 24 surrounding pixels within the 5x5 window will be pink.
  2. This illustrate how the temporal moving window considers data from multiple layers (time steps) when smoothing the value for a single pixel.

The moving window approach is used to balance the advantages of capturing both spatial and temporal variations in precipitation patterns. By considering both spatial and temporal windows, the bias correction method can address local variations and seasonal changes more effectively.

Spatial Moving Window illustration

spatial_moving_window

Temporal Moving Window illustration

temporal_moving_window

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import matplotlib.patches as mpatches
# Create synthetic data for 3 layers
np.random.seed(42)
layers = 3
grid_size = 10
data = np.random.gamma(2, 2, size=(layers, grid_size, grid_size))
# Create 3D plot
fig = plt.figure(figsize=(12, 8))
ax = fig.add_subplot(111, projection='3d')
# Plot each layer
for i in range(layers):
x, y = np.meshgrid(range(grid_size), range(grid_size))
z = np.full_like(x, i)
ax.plot_surface(x, y, z, facecolors=plt.cm.Blues(data[i]/np.max(data)), alpha=0.3)
# Highlight the selected pixel at (4,5) in the top layer
selected_layer = layers - 1
x, y = 4, 5
# Add a red cube to highlight the selected pixel
ax.bar3d(x, y, selected_layer, 1, 1, 0.1, color='red', alpha=0.7)
# Show the spatial window (5x5)
window_size = 5
for i in range(x - window_size//2, x + window_size//2 + 1):
for j in range(y - window_size//2, y + window_size//2 + 1):
if 0 <= i < grid_size and 0 <= j < grid_size and (i != x or j != y):
ax.bar3d(i, j, selected_layer, 1, 1, 0.1, color='pink', alpha=0.5)
# Set labels and title
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Layer')
ax.set_title('Spatial Moving Window Visualization (5x5)')
# Set the viewing angle
ax.view_init(elev=20, azim=45)
# Create custom legend
red_patch = mpatches.Patch(color='red', label='Selected Pixel (4,5)')
pink_patch = mpatches.Patch(color='pink', label='Spatial Window (5x5)')
ax.legend(handles=[red_patch, pink_patch])
# Set axis limits
ax.set_xlim(0, grid_size)
ax.set_ylim(0, grid_size)
ax.set_zlim(0, layers-1)
# Set tick labels
ax.set_xticks(range(grid_size))
ax.set_yticks(range(grid_size))
ax.set_zticks(range(layers))
plt.show()
import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import matplotlib.patches as mpatches
# Create synthetic data for 8 layers
np.random.seed(42)
layers = 8
grid_size = 5
data = np.random.gamma(2, 2, size=(layers, grid_size, grid_size))
# Function to apply temporal moving window
def apply_temporal_window(data, window_size=5):
padded_data = np.pad(data, ((window_size//2, window_size//2), (0, 0), (0, 0)), mode='edge')
result = np.zeros_like(data)
for i in range(layers):
result[i] = np.mean(padded_data[i:i+window_size], axis=0)
return result
# Apply temporal moving window
smoothed_data = apply_temporal_window(data)
# Create 3D plot
fig = plt.figure(figsize=(12, 8))
ax = fig.add_subplot(111, projection='3d')
# Plot each layer
for i in range(layers):
x, y = np.meshgrid(range(grid_size), range(grid_size))
z = np.full_like(x, i)
ax.plot_surface(x, y, z, facecolors=plt.cm.Blues(data[i]/np.max(data)), alpha=0.3)
# Highlight the central pixel at (4,4) in the middle layer
middle_layer = layers // 2
x, y = 4, 4
# Add a red cube to highlight the entire pixel
ax.bar3d(x, y, middle_layer, 1, 1, 0.1, color='red', alpha=0.7)
# Show the temporal window
window_size = 5
for i in range(middle_layer - window_size//2, middle_layer + window_size//2 + 1):
if i != middle_layer:
ax.bar3d(x, y, i, 1, 1, 0.1, color='pink', alpha=0.5)
ax.plot([x+0.5, x+0.5], [y+0.5, y+0.5], [i, middle_layer], color='pink', linestyle='--', alpha=0.5)
# Set labels and title
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Layer')
ax.set_title('Temporal Moving Window Visualization')
# Set the viewing angle
ax.view_init(elev=20, azim=45)
# Create custom legend
red_patch = mpatches.Patch(color='red', label='Central Pixel (4,4)')
pink_patch = mpatches.Patch(color='pink', label='Temporal Window (±2 layers)')
ax.legend(handles=[red_patch, pink_patch])
# Set axis limits
ax.set_xlim(0, grid_size)
ax.set_ylim(0, grid_size)
ax.set_zlim(0, layers-1)
# Set tick labels
ax.set_xticks(range(grid_size))
ax.set_yticks(range(grid_size))
ax.set_zticks(range(layers))
plt.show()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment