Last active
August 23, 2024 05:26
-
-
Save dashmage/2aac098c09d4e6d31488e6d000e3fc2f to your computer and use it in GitHub Desktop.
Knuth/ Fisher-Yates Shuffle Animation
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
""" | |
Knuth/ Fisher-Yates shuffle algorithm visualized with the manim library. | |
Install manim (preferably in a virtual environment), | |
$ pip install manim | |
Generate the animation play the resulting mp4 file, | |
$ manim -pql scene.py KnuthShuffle | |
To generate a higher quality animation once you're done testing the code (takes more time to execute), | |
$ manim -qh scene.py KnuthShuffle | |
""" | |
from manim import * | |
import random | |
class KnuthShuffle(Scene): | |
def construct(self): | |
# Initial list | |
data = ["A", "B", "C", "D", "E"] | |
# Create text objects for the list elements | |
elements = [Text(str(num)) for num in data] | |
# Create white square outlines for the elements | |
outlines = [Square(side_length=1.2, color=WHITE) for _ in data] | |
for i, (element, outline) in enumerate(zip(elements, outlines)): | |
element.move_to(DOWN * 1.2 + RIGHT * (i * 1.2 - 4) + 1.2) | |
outline.move_to(element.get_center()) | |
self.play(*[Write(element) for element in elements]) | |
self.play(*[Create(outline) for outline in outlines]) | |
self.wait() | |
for i in range(len(data) - 1, 0, -1): | |
# Random index between 0 and i | |
j = random.randint(0, i) | |
if i != j: | |
arrow = CurvedDoubleArrow(elements[i].get_bottom() + DOWN * 0.5, elements[j].get_bottom() + DOWN * 0.5, color=RED, angle=-TAU/4) | |
else: | |
arrow = CurvedDoubleArrow(elements[i].get_bottom() + DOWN * 0.5 + RIGHT * 0.5, elements[j].get_bottom() + DOWN * 0.5 + LEFT * 0.5, color=RED, angle=-TAU/4) | |
self.play(FadeIn(arrow)) | |
self.wait(0.5) | |
# Swap the elements in the list | |
data[i], data[j] = data[j], data[i] | |
# Animate the swap | |
self.play( | |
elements[i].animate.move_to(elements[j].get_center()), | |
elements[j].animate.move_to(elements[i].get_center()), | |
outlines[i].animate.move_to(outlines[j].get_center()), | |
outlines[j].animate.move_to(outlines[i].get_center()) | |
) | |
# Update their positions in the list | |
elements[i], elements[j] = elements[j], elements[i] | |
outlines[i], outlines[j] = outlines[j], outlines[i] | |
self.wait(0.5) | |
self.play(outlines[i].animate.set_fill(PINK, opacity=0.2)) | |
# Remove the arrow | |
self.play(FadeOut(arrow)) | |
# Final wait before ending the scene | |
self.wait(2) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
knuth_shuffle.mp4