Math.random生成不重复结果、避免条件失效及Vine生成器近期去重问题
Hey there! Let's break this down for you—you want to generate non-repeating random results with Math.random() (fixing that conditional logic issue you ran into) and make your Vine generator avoid repeating the last 3 entries. Here's how to do it right:
核心思路:维护最近记录 + 循环重试
The key fix here is keeping track of the last 3 Vine entries you've generated, and looping until you pick a new one that isn't in that recent list. A lot of conditional logic failures happen when you only check once (instead of retrying) or don't properly update your recent entries list.
完整代码实现
Using your existing vines array, here's a working implementation that guarantees no repeats in the last 3 generated items:
// Your existing Vine dataset const vines = [ ['https://www.youtube.com/watch?v=21yI4dtAyJQ', 'Gotta love dogs'], ['https://www.youtube.com/watch?v=MB1Ud95U8FE', 'The struggle of measuring something without measuring tape'], ['https://www.youtube.com/watch?v=b6l63-AdU6Y', 'When...'] ]; // Store indexes of the last 3 generated Vines (using indexes is more efficient than full entries) let recentVineIndexes = []; function generateRandomVine() { let randomIndex; // Loop until we find an index NOT in the recent list do { // Generate a valid random index for the vines array randomIndex = Math.floor(Math.random() * vines.length); } while (recentVineIndexes.includes(randomIndex)); // Update the recent list: add the new index, trim to keep only last 3 recentVineIndexes.push(randomIndex); if (recentVineIndexes.length > 3) { recentVineIndexes.shift(); // Remove the oldest entry } // Return the selected Vine entry return vines[randomIndex]; } // Test it out! for (let i = 0; i < 5; i++) { const [url, description] = generateRandomVine(); console.log(`Vine ${i + 1}: ${description} (${url})`); }
Why Your Old Conditional Logic Might Have Failed
If your previous code only checked once for repeats (like the example below), it could still end up returning a duplicate because the second random pick might also be in the recent list—no second check means your conditional was effectively ignored:
// ❌ Bad example: only checks once, can still return duplicates let randomIndex = Math.floor(Math.random() * vines.length); if (recentVineIndexes.includes(randomIndex)) { randomIndex = Math.floor(Math.random() * vines.length); }
The do...while loop fixes this by keeping retrying until it finds a valid, non-repeating entry.
Edge Case Handling
If your vines array has 3 or fewer entries, it's impossible to avoid repeats (since you're trying to exclude the last 3). Add this check to handle that scenario gracefully:
function generateRandomVine() { // Handle small dataset edge case if (vines.length <= 3) { console.warn("Not enough Vine entries to guarantee no repeats in last 3"); return vines[Math.floor(Math.random() * vines.length)]; } // Rest of the function stays the same... }
内容的提问来源于stack exchange,提问作者Unkn0wn

