簡體   English   中英

在 n-1 天內將 n 人以不同的對分配的算法

[英]Algorithm to distribute n people in unique pairs over n-1 days

我正在嘗試創建一種算法,該算法可以從偶數 n 人中創建獨特的配對。 之后,它應該將這些對划分為 n-1 天。 所以每一天,每個人都會遇到另一個人。 對不應重復。 該算法應在每次運行時提供不同的解決方案。

例如,我的起始數組是 [1,2,3,4] - 這將轉換為以下對:

[1,2],[1,3],[1,4],
      [2,3],[2,4],
            [3,4]

現在這些對需要像這樣在 n-1 天之間拆分

day 1 [1,2] & [3,4]
day 2 [1,3] & [2,4]
day 3 [1,4] & [2,3]

感謝您的幫助!

更新

感謝我寫了這個解決方案的答案

    fun createDates(userIds: List<Int>): List<DateEntity> {
        val dates = ArrayList<DateEntity>()

        val userCount = userIds.size
        val days = userCount - 1
        val half = userCount / 2

        val mutableUsers = userIds.toMutableList()

        for (day in 0 until days) {
            val firstHalf = mutableUsers.slice(0 until half)
            val secondHalf = mutableUsers.slice(half until userCount).reversed()

            for (i in firstHalf.indices) {
                dates.add(DateEntity(day, firstHalf[i], secondHalf[i]))
            }
            // rotating the array
            mutableUsers.add(1, mutableUsers.removeLast())
        }
        return dates
    }

循環算法:

把人排成兩排。

每天,上排的人與下排的相應人配對。 如果人數是奇數,一個人等一天。

day 1
A B C
D E F
A:D B:E C:F

白班結束后,除了第一個人以外的所有人都以循環方式:

day 2
A D B
E F C
A:E D:F B:C 

day 3
A E D
F C B
A:F E:C D:B

等等。

此代碼僅執行 MBo 描述的算法

 const cycle = (n, xs) => [... xs.slice (n % xs.length), ... xs.slice (0, n % xs.length)] const pairs = (xs) => xs.length < 2? []: [[xs [0], xs [xs.length - 1]], ...pairs (xs.slice (1, -1))] const roundRobin = ([x, ...xs]) => Array.from(xs, (_, i) => pairs ([x, ...cycle(i, xs)])) console.log (roundRobin ([1, 2, 3, 4, 5, 6])) //=> // (1 - 6) & (2 - 5) & (3 - 4) // (1 - 2) & (3 - 6) & (4 - 5) // (1 - 3) & (4 - 2) & (5 - 6) // (1 - 4) & (5 - 3) & (6 - 2) // (1 - 5) & (6 - 4) & (2 - 3)
 .as-console-wrapper {max-height: 100%;important: top: 0}

cycle只是循環一個數組n位置,例如, cycle (2, ['a', 'b', 'c', 'd', 'e'])產生['c', 'd', 'e', 'a', 'b'] pairs將數組末端的兩個元素配對,然后將它們旁邊的兩個元素配對,以此類推。 pairs (['a', 'b', 'c', 'd', 'e', 'f'])產生[['a', 'f'], ['b', 'e'], ['c', 'd']]

我們將這些組合在roundRobin中,對於每一天,我們刪除第一個值,循環剩余的值,將第一個值放回原處,然后將列表變成對。

如果您想要額外的隨機性,我建議您在開始之前簡單地改組數組。

如果你想允許奇數個參與者,每次一個人坐在外面,我會添加一個專門的不坐參與者,然后每天與不同的參與者配對。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM