【JS】三十行代碼實現洗牌效果

/**
 * 創建基本卡組
 *
 * 思路
 * 1. Array.from轉化基本花色字符串爲數組
 * 2. 利用map進行初始化花色以及基本數字, 設置level屬性爲排序數組做準備
 * 3. [].concat()平鋪數組
 * @returns {Array} 返回type長度的二維數組
 */
const createDeck = (function(){
    const type = "♠♥♦♣" // 基本花色
    const base = ["3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K", "A", "2"] // 牌組

    return [].concat(...Array.from(type, item => {
        return base.map( (v, key) => ({val: item + v, level: key}))
    }), {val: "大王", level: 13},  {val: "小王", level: 13})
})()

/**
 * 返回指定範圍的隨機數
 *
 * @param {number} [min] 最小值
 * @param {number} [min] 最大值
 * @returns {number} 數組下標
 */
function getRandom(min, max){
    return Math.floor(Math.random() * (max - min) + min);
}

/**
 * 生成隨機卡組
 *
 * 思路
 * 1. Array.from初始化卡組長度
 * 2. 隨機抽取數組元素
 * 3. 根據level屬性進行重排序
 * @returns {Array} 返回len長度的隨機數組
 */
function createGrop(len){
    let cardNum = createDeck.length / len // 牌數
    let copy = createDeck.concat()        // 獲取基本卡組, 通過concat解引

    return Array.from({length: len}, () => {
        const sortHandle = (a, b) => b.level - a.level; // 重排序方法
        let _, arr = [] 

        // 如果長度爲最後立即返回,即後面的隨機抽取已沒意義
        if(copy.length == 18) return copy.sort(sortHandle).map(v => v.val);

        _ = function grop(){ // 自調用寫法
            if(arr.length == cardNum) return; // 達到指定手牌數即終止
            let cur = getRandom(0, copy.length)

            if(arr.map(v => v.val).includes(copy[cur].val)){ // 檢測是否已存在
                return grop() // 如果存在重新獲取隨機數
            } else {
                arr.push(copy[cur]) 
                copy.splice(cur, 1) // 刪除原數組中已被抽取的數子
                grop()
            }
        }() 
        arr = arr.sort(sortHandle).map(v => v.val) // 重排序數組,並刪除level屬性

        return arr
    })
}
console.log(createGrop(3)) // -↓
/*
0: (18) ["大王", "♠2", "♣A", "♦K", "♣K", "♥K", "♥Q", "♣J", "♣10", "♥10", "♦8", "♦7", "♠6", "♥6", "♥4", "♠4", "♣3", "♠3"]
1: (18) ["小王", "♦2", "♥A", "♦A", "♠A", "♠K", "♣Q", "♠Q", "♠J", "♥J", "♦9", "♣9", "♥8", "♣7", "♣6", "♠5", "♣4", "♥3"]
2: (18) ["♥2", "♣2", "♦Q", "♦J", "♠10", "♦10", "♠9", "♥9", "♠8", "♣8", "♠7", "♥7", "♦6", "♥5", "♦5", "♣5", "♦4", "♦3"]
*/

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章