排序动画效果

冒泡排序算法可视化效果实现

<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>排序动画效果</title>
    <style>
        body {
            font-family: 'Arial', sans-serif;
            display: flex;
            flex-direction: column;
            align-items: center;
            background-color: #f5f5f5;
            padding: 20px;
        }
        
        h1 {
            color: #333;
            margin-bottom: 30px;
        }
        
        .container {
            width: 80%;
            max-width: 800px;
            margin: 0 auto;
        }
        
        .array-container {
            display: flex;
            justify-content: center;
            align-items: flex-end;
            height: 400px;
            margin-bottom: 30px;
            background-color: white;
            border-radius: 8px;
            box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
            padding: 20px;
        }
        
        .array-bar {
            width: 30px;
            margin: 0 2px;
            background-color: #4CAF50;
            transition: height 0.3s ease, background-color 0.3s ease;
            border-radius: 3px 3px 0 0;
            position: relative;
        }
        
        .array-bar.comparing {
            background-color: #FF5722;
        }
        
        .array-bar.sorted {
            background-color: #2196F3;
        }
        
        .array-bar.swapping {
            background-color: #9C27B0;
        }
        
        .bar-value {
            position: absolute;
            top: -25px;
            width: 100%;
            text-align: center;
            font-size: 12px;
            color: #333;
        }
        
        .controls {
            display: flex;
            justify-content: center;
            gap: 15px;
            margin-bottom: 20px;
        }
        
        button {
            padding: 10px 20px;
            background-color: #4CAF50;
            color: white;
            border: none;
            border-radius: 4px;
            cursor: pointer;
            font-size: 16px;
            transition: background-color 0.3s;
        }
        
        button:hover {
            background-color: #45a049;
        }
        
        button:disabled {
            background-color: #cccccc;
            cursor: not-allowed;
        }
        
        .speed-control {
            display: flex;
            align-items: center;
            gap: 10px;
        }
        
        .speed-control label {
            font-weight: bold;
        }
        
        .speed-control input {
            width: 150px;
        }
        
        .info {
            margin-top: 20px;
            padding: 15px;
            background-color: #e9f7ef;
            border-radius: 4px;
            color: #333;
            text-align: center;
        }
        
        .sponsor {
            margin-top: 30px;
            font-size: 14px;
            color: #666;
            text-align: center;
        }
        
        .sponsor a {
            color: #4CAF50;
            text-decoration: none;
        }
        
        .sponsor a:hover {
            text-decoration: underline;
        }
    </style>
</head>
<body>
    <div class="container">
        <h1>排序算法可视化</h1>
        
        <div class="controls">
            <button id="generate-btn">生成新数组</button>
            <button id="bubble-sort-btn">冒泡排序</button>
            <button id="reset-btn">重置</button>
        </div>
        
        <div class="speed-control">
            <label for="speed">排序速度:</label>
            <input type="range" id="speed" min="1" max="10" value="5">
        </div>
        
        <div class="array-container" id="array-container"></div>
        
        <div class="info" id="info">
            点击"生成新数组"创建随机数组,然后选择排序算法开始可视化。
        </div>
        
        <div class="sponsor">

        </div>
    </div>

    <script>
        // 全局变量
        let array = [];
        let animationSpeed = 200;
        let isSorting = false;
        let animationQueue = [];
        
        // DOM元素
        const arrayContainer = document.getElementById('array-container');
        const generateBtn = document.getElementById('generate-btn');
        const bubbleSortBtn = document.getElementById('bubble-sort-btn');
        const resetBtn = document.getElementById('reset-btn');
        const speedControl = document.getElementById('speed');
        const infoDiv = document.getElementById('info');
        
        // 初始化
        generateNewArray();
        
        // 事件监听
        generateBtn.addEventListener('click', generateNewArray);
        bubbleSortBtn.addEventListener('click', startBubbleSort);
        resetBtn.addEventListener('click', resetArray);
        speedControl.addEventListener('input', updateSpeed);
        
        // 生成新数组
        function generateNewArray() {
            if (isSorting) return;
            
            array = [];
            const arraySize = Math.floor(Math.random() * 15) + 10; // 10-24个元素
            
            for (let i = 0; i < arraySize; i++) {
                array.push(Math.floor(Math.random() * 100) + 5); // 5-104之间的随机数
            }
            
            renderArray();
            infoDiv.textContent = "新数组已生成,请选择排序算法开始可视化。";
        }
        
        // 渲染数组
        function renderArray() {
            arrayContainer.innerHTML = '';
            
            const maxValue = Math.max(...array);
            const containerHeight = arrayContainer.clientHeight;
            
            array.forEach((value, index) => {
                const bar = document.createElement('div');
                bar.className = 'array-bar';
                bar.style.height = `${(value / maxValue) * (containerHeight - 30)}px`;
                
                const valueLabel = document.createElement('div');
                valueLabel.className = 'bar-value';
                valueLabel.textContent = value;
                
                bar.appendChild(valueLabel);
                arrayContainer.appendChild(bar);
            });
        }
        
        // 更新速度
        function updateSpeed() {
            animationSpeed = 220 - (speedControl.value * 20);
        }
        
        // 重置数组
        function resetArray() {
            if (isSorting) return;
            renderArray();
            infoDiv.textContent = "数组已重置为当前状态。";
        }
        
        // 开始冒泡排序
        function startBubbleSort() {
            if (isSorting) return;
            
            isSorting = true;
            disableButtons();
            infoDiv.textContent = "冒泡排序进行中...";
            
            // 复制数组用于排序
            const sortingArray = [...array];
            animationQueue = [];
            
            // 生成动画队列
            bubbleSort(sortingArray);
            
            // 执行动画
            playAnimations();
        }
        
        // 冒泡排序算法
        function bubbleSort(arr) {
            const n = arr.length;
            
            for (let i = 0; i < n - 1; i++) {
                for (let j = 0; j < n - i - 1; j++) {
                    // 添加比较动画
                    animationQueue.push({
                        type: 'compare',
                        indices: [j, j + 1]
                    });
                    
                    if (arr[j] > arr[j + 1]) {
                        // 添加交换动画
                        animationQueue.push({
                            type: 'swap',
                            indices: [j, j + 1]
                        });
                        
                        // 实际交换数组元素
                        [arr[j], arr[j + 1]] = [arr[j + 1], arr[j]];
                    }
                    
                    // 添加比较结束动画
                    animationQueue.push({
                        type: 'reset',
                        indices: [j, j + 1]
                    });
                }
                
                // 标记已排序的元素
                animationQueue.push({
                    type: 'sorted',
                    index: n - i - 1
                });
            }
            
            // 标记最后一个元素为已排序
            animationQueue.push({
                type: 'sorted',
                index: 0
            });
        }
        
        // 播放动画
        function playAnimations() {
            if (animationQueue.length === 0) {
                sortingComplete();
                return;
            }
            
            const animation = animationQueue.shift();
            const bars = document.querySelectorAll('.array-bar');
            
            switch (animation.type) {
                case 'compare':
                    bars[animation.indices[0]].classList.add('comparing');
                    bars[animation.indices[1]].classList.add('comparing');
                    break;
                    
                case 'swap':
                    const [i, j] = animation.indices;
                    const tempHeight = bars[i].style.height;
                    bars[i].style.height = bars[j].style.height;
                    bars[j].style.height = tempHeight;
                    
                    // 交换数值显示
                    const tempValue = bars[i].querySelector('.bar-value').textContent;
                    bars[i].querySelector('.bar-value').textContent = bars[j].querySelector('.bar-value').textContent;
                    bars[j].querySelector('.bar-value').textContent = tempValue;
                    
                    bars[i].classList.add('swapping');
                    bars[j].classList.add('swapping');
                    break;
                    
                case 'reset':
                    bars[animation.indices[0]].classList.remove('comparing', 'swapping');
                    bars[animation.indices[1]].classList.remove('comparing', 'swapping');
                    break;
                    
                case 'sorted':
                    bars[animation.index].classList.add('sorted');
                    break;
            }
            
            setTimeout(() => {
                playAnimations();
            }, animationSpeed);
        }
        
        // 排序完成
        function sortingComplete() {
            isSorting = false;
            enableButtons();
            infoDiv.textContent = "冒泡排序完成!";
        }
        
        // 禁用按钮
        function disableButtons() {
            generateBtn.disabled = true;
            bubbleSortBtn.disabled = true;
            resetBtn.disabled = true;
        }
        
        // 启用按钮
        function enableButtons() {
            generateBtn.disabled = false;
            bubbleSortBtn.disabled = false;
            resetBtn.disabled = false;
        }
    </script>
</body>
</html>

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值