Build an RNN With Python
In this lesson, we will build a simple Recurrent Neural Network using TensorFlow and Keras. We will use sequence data to teach the RNN to predict the next value.
What Are We Building?
Suppose we have this sequence:
10, 20, 30, 40, 50, 60
We want the RNN to learn the pattern and predict the next number.
10, 20, 30 → 40
20, 30, 40 → 50
30, 40, 50 → 60
So the model receives a sequence of numbers and tries to predict the number that comes next.
Step 1 — Import TensorFlow
import tensorflow as tf
TensorFlow provides the tools we need to build and train the neural network.
Keras is included inside TensorFlow and gives us a simple way to create the RNN.
Step 2 — Create the Training Data
import numpy as np
X = np.array([
[10, 20, 30],
[20, 30, 40],
[30, 40, 50]
])
y = np.array([
40,
50,
60
])
Here, each row in X is one sequence.
[10, 20, 30] → 40
[20, 30, 40] → 50
[30, 40, 50] → 60
X contains the input sequences.
y contains the correct answers.
Step 3 — Understand the Input Shape
RNNs expect sequence data in three dimensions:
(samples, time steps, features)
Our data currently has:
3 samples
3 time steps
1 feature
Therefore, we reshape the data:
X = X.reshape(3, 3, 1)
Now the shape is:
(3, 3, 1)
This means:
3
↓
Number of sequences
3
↓
Number of time steps in each sequence
1
↓
One feature at each time step
Visualizing the Input
Sequence 1
10 → 20 → 30
↓
40
Sequence 2
20 → 30 → 40
↓
50
Sequence 3
30 → 40 → 50
↓
60
This is exactly the type of pattern an RNN can learn: information arrives in a specific order.
Step 4 — Create the RNN
model = tf.keras.Sequential([
tf.keras.layers.SimpleRNN(16, activation="tanh"),
tf.keras.layers.Dense(1)
])
We have created two layers.
SimpleRNN(16)
↓
Learns sequence patterns
Dense(1)
↓
Produces one prediction
The number 16 means the RNN has 16 hidden
units.
The Dense(1) layer produces one output
because we want to predict one number.
Step 5 — Compile the Model
model.compile(
optimizer="adam",
loss="mse"
)
The optimizer controls how the model updates its weights.
We use adam because it is a common optimizer
for neural networks.
mse means Mean Squared Error.
Since we are predicting a number, MSE is a suitable loss function for this simple example.
Step 6 — Train the RNN
model.fit(
X,
y,
epochs=500,
verbose=0
)
During training, the model repeatedly looks at the sequences and compares its predictions with the correct answers.
Input
↓
RNN
↓
Prediction
↓
Calculate Loss
↓
Backpropagation
↓
Update Weights
↓
Repeat
epochs=500 means the model goes through the
training data 500 times.
For a real project, you would not blindly choose 500. You would monitor training and validation performance.
Step 7 — Make a Prediction
test_input = np.array([[
[40],
[50],
[60]
]])
prediction = model.predict(test_input)
print(prediction)
We give the model:
40 → 50 → 60
The pattern suggests:
70
After successful training, the prediction should be reasonably close to 70.
Complete Python Code
import numpy as np
import tensorflow as tf
# Training data
X = np.array([
[10, 20, 30],
[20, 30, 40],
[30, 40, 50]
])
y = np.array([
40,
50,
60
])
# Reshape for RNN
X = X.reshape(3, 3, 1)
# Create model
model = tf.keras.Sequential([
tf.keras.layers.SimpleRNN(
16,
activation="tanh"
),
tf.keras.layers.Dense(1)
])
# Compile model
model.compile(
optimizer="adam",
loss="mse"
)
# Train model
model.fit(
X,
y,
epochs=500,
verbose=0
)
# Test data
test_input = np.array([
[
[40],
[50],
[60]
]
])
# Make prediction
prediction = model.predict(test_input)
print("Predicted next value:", prediction[0][0])
Understand the Complete Flow
Training Data
10 → 20 → 30 → 40
20 → 30 → 40 → 50
30 → 40 → 50 → 60
↓
Reshape Data
(samples, time steps, features)
↓
SimpleRNN(16)
↓
Dense(1)
↓
Prediction
↓
Calculate MSE Loss
↓
Adam Optimizer
↓
Update Weights
↓
Repeat for many epochs
This is the complete training process in a simplified form.
Understand the Most Important Part — Shape
If you remember only one technical detail from this lesson, remember the RNN input shape:
(samples, time steps, features)
For our example:
(3, 3, 1)
Think of it as:
3 sequences
Sequence 1:
10 → 20 → 30
Sequence 2:
20 → 30 → 40
Sequence 3:
30 → 40 → 50
Each time step has:
1 feature
If the input has multiple features, the last number changes.
(samples, time steps, features)
Example:
(100, 10, 3)
100 sequences
10 time steps
3 features at each step
Another Example — Temperature Prediction
RNNs are useful when the order of data matters. For example, suppose we have temperatures:
Monday 25°C
Tuesday 27°C
Wednesday 29°C
We could use the previous three days to predict the next day:
25 → 27 → 29
↓
predict
↓
31
The same basic RNN structure can be used:
Sequence
↓
SimpleRNN
↓
Dense
↓
Prediction
Important: This Is a Learning Example
The number sequence in this example is intentionally simple:
10, 20, 30, 40, 50, 60...
A model can learn this pattern very easily.
Real-world sequence data is much more complicated. For example:
Stock prices
Weather measurements
Sensor data
Text
Speech
Time-series data
Real data usually contains noise, missing values, changing patterns, and much more complicated dependencies.
So this example teaches you how to build and use an RNN, not how to solve a production-level forecasting problem.
Final Summary
1. Create sequence data
↓
2. Reshape data
↓
3. Create SimpleRNN
↓
4. Add output layer
↓
5. Compile model
↓
6. Train model
↓
7. Give new sequence
↓
8. Make prediction
The most important code to remember is:
model = tf.keras.Sequential([
tf.keras.layers.SimpleRNN(16),
tf.keras.layers.Dense(1)
])
model.compile(
optimizer="adam",
loss="mse"
)
model.fit(X, y, epochs=500)
In simple words:
SimpleRNN
↓
Learn patterns from sequence
Dense
↓
Produce prediction
Check Your Understanding
1. What does an RNN receive?
A sequence of data arranged across time steps.
2. What is the RNN input shape?
(samples, time steps, features).
3. Why do we use Dense(1)?
Because we want one numerical prediction.
4. Why do we use MSE?
We are predicting a continuous numerical value.
5. What does model.fit() do?
It trains the model by repeatedly making predictions,
calculating loss, computing gradients, and updating
weights.