这是一个通过迭代实现组合的
go
实现,按照输入顺序排列
(适用于组合和每个组合中的项)。
代码 (go)
package combination_util
import (
"fmt"
"golang.org/x/exp/constraints"
)
func CombInOrderCountViaIter[T constraints.Ordered](is []T, m int, h HandlerCount[T]) int {
n := len(is)
if m < 0 || n < m {
return 0
}
seq := 0
if m == 0 {
h(is, nil, &seq)
return 1
}
indices := make([]int, m)
for i := 0; i < m; i++ {
indices[i] = i
}
li := m - 1
maxIdx := n - 1
h(is, indices, &seq)
endIdxForFirst := n - m
if n > m {
outer:
for {
if indices[li] < maxIdx {
indices[li]++
h(is, indices, &seq)
} else if m > 1 {
curIdx, preIdx := li, li-1
for {
indices[preIdx]++
if indices[curIdx]-indices[preIdx] == 1 {
h(is, indices, &seq)
if preIdx == 0 && indices[0] == endIdxForFirst {
break outer
}
} else {
for i, delta := curIdx, 1; i < m; i, delta = i+1, delta+1 {
indices[i] = indices[preIdx] + delta
}
h(is, indices, &seq)
break
}
curIdx--
preIdx--
}
} else {
break
}
}
}
return seq
}
func CombInOrderCountViaIterAsIndex(n, m int, h HandlerCount[int]) int {
is := GenInputAsIndex(n)
return CombInOrderCountViaIter(is, m, h)
}
func CombInOrderCountAndPrintViaIterAsIndex(n, m int) int {
PrintInputAsIndex(n, m, true)
return CombInOrderCountViaIterAsIndex(n, m, HandlerCountImplPrint[int])
}
func CombInOrderCountAndPrintPatternViaIterAsIndex(n, m int) int {
PrintInputAsIndex(n, m, true)
return CombInOrderCountViaIterAsIndex(n, m, HandlerCountImplPrintPattern[int])
}
func indicesToComb[T constraints.Ordered](is []T, flags []int) []T {
m := len(flags)
comb := make([]T, m)
for i := 0; i < m; i++ {
comb[i] = is[flags[i]]
}
return comb
}
func PrintInput[T constraints.Ordered](is []T, m int, prependNewLine bool) {
prefix := ""
if prependNewLine {
prefix = "\n"
}
fmt.Printf("%s%v, m = %d:\n", prefix, is, m)
}
func PrintInputAsIndex(n, m int, prependNewLine bool) {
is := GenInputAsIndex(n)
PrintInput[int](is, m, prependNewLine)
}
func GenInputAsIndex(n int) []int {
is := make([]int, n)
for i := 0; i < n; i++ {
is[i] = i
}
return is
}
const (
BlackSquare = '◼'
WhiteSquare = '◻'
)
type HandlerCount[T constraints.Ordered] func(is []T, indices []int, seq *int)
func HandlerCountImplPrint[T constraints.Ordered](is []T, indices []int, seq *int) {
comb := indicesToComb(is, indices)
fmt.Printf("\t(%d)\t%v\n", *seq, comb)
*seq++
}
func HandlerCountImplPrintPattern[T constraints.Ordered](is []T, indices []int, seq *int) {
n := len(is)
pattern := make([]rune, n)
for i := 0; i < n; i++ {
pattern[i] = WhiteSquare
}
for _, index := range indices {
pattern[index] = BlackSquare
}
fmt.Printf("\t%s\t(%d)\n", string(pattern), *seq)
*seq++
}
测试
func main() {
CombInOrderCountAndPrintViaIterAsIndex(5, 3)
CombInOrderCountAndPrintPatternViaIterAsIndex(10, 5)
}
输出
print combination, via CombInOrderCountAndPrintViaIterAsIndex()
n = 5
, m = 3
, generated input = [0 1 2 3 4]
:
(0) [0 1 2]
(1) [0 1 3]
(2) [0 1 4]
(3) [0 2 3]
(4) [0 2 4]
(5) [0 3 4]
(6) [1 2 3]
(7) [1 2 4]
(8) [1 3 4]
(9) [2 3 4]
print pattern, via CombInOrderCountAndPrintPatternViaIterAsIndex()
n = 10
, m = 5
, generated input = [0 1 2 3 4 5 6 7 8 9]
:
◼◼◼◼◼◻◻◻◻◻ (0)
◼◼◼◼◻◼◻◻◻◻ (1)
◼◼◼◼◻◻◼◻◻◻ (2)
◼◼◼◼◻◻◻◼◻◻ (3)
◼◼◼◼◻◻◻◻◼◻ (4)
◼◼◼◼◻◻◻◻◻◼ (5)
◼◼◼◻◼◼◻◻◻◻ (6)
◼◼◼◻◼◻◼◻◻◻ (7)
◼◼◼◻◼◻◻◼◻◻ (8)
◼◼◼◻◼◻◻◻◼◻ (9)
◼◼◼◻◼◻◻◻◻◼ (10)
◼◼◼◻◻◼◼◻◻◻ (11)
◼◼◼◻◻◼◻◼◻◻ (12)
◼◼◼◻◻◼◻◻◼◻ (13)
◼◼◼◻◻◼◻◻◻◼ (14)
◼◼◼◻◻◻◼◼◻◻ (15)
◼◼◼◻◻◻◼◻◼◻ (16)
◼◼◼◻◻◻◼◻◻◼ (17)
◼◼◼◻◻◻◻◼◼◻ (18)
◼◼◼◻◻◻◻◼◻◼ (19)
◼◼◼◻◻◻◻◻◼◼ (20)
◼◼◻◼◼◼◻◻◻◻ (21)
◼◼◻◼◼◻◼◻◻◻ (22)
◼◼◻◼◼◻◻◼◻◻ (23)
◼◼◻◼◼◻◻◻◼◻ (24)
◼◼◻◼◼◻◻◻◻◼ (25)
◼◼◻◼◻◼◼◻◻◻ (26)
◼◼◻◼◻◼◻◼◻◻ (27)
◼◼◻◼◻◼◻◻◼◻ (28)
◼◼◻◼◻◼◻◻◻◼ (29)
◼◼◻◼◻◻◼◼◻◻ (30)
◼◼◻◼◻◻◼◻◼◻ (31)
◼◼◻◼◻◻◼◻◻◼ (32)
◼◼◻◼◻◻◻◼◼◻ (33)
◼◼◻◼◻◻◻◼◻◼ (34)
◼◼◻◼◻◻◻◻◼◼ (35)
◼◼◻◻◼◼◼◻◻◻ (36)
◼◼◻◻◼◼◻◼◻◻ (37)
◼◼◻◻◼◼◻◻◼◻ (38)
◼◼◻◻◼◼◻◻◻◼ (39)
◼◼◻◻◼◻◼◼◻◻ (40)
◼◼◻◻◼◻◼◻◼◻ (41)
◼◼◻◻◼◻◼◻◻◼ (42)
◼◼◻◻◼◻◻◼◼◻ (43)
◼◼◻◻◼◻◻◼◻◼ (44)
◼◼◻◻◼◻◻◻◼◼ (45)
◼◼◻◻◻◼◼◼◻◻ (46)
◼◼◻◻◻◼◼◻◼◻ (47)
◼◼◻◻◻◼◼◻◻◼ (48)
◼◼◻◻◻◼◻◼◼◻ (49)
◼◼◻◻◻◼◻◼◻◼ (50)
◼◼◻◻◻◼◻◻◼◼ (51)
◼◼◻◻◻◻◼◼◼◻ (52)
◼◼◻◻◻◻◼◼◻◼ (53)
◼◼◻◻◻◻◼◻◼◼ (54)
◼◼◻◻◻◻◻◼◼◼ (55)
◼◻◼◼◼◼◻◻◻◻ (56)
◼◻◼◼◼◻◼◻◻◻ (57)
◼◻◼◼◼◻◻◼◻◻ (58)
◼◻◼◼◼◻◻◻◼◻ (59)
◼◻◼◼◼◻◻◻◻◼ (60)
◼◻◼◼◻◼◼◻◻◻ (61)
◼◻◼◼◻◼◻◼◻◻ (62)
◼◻◼◼◻◼◻◻◼◻ (63)
◼◻◼◼◻◼◻◻◻◼ (64)
◼◻◼◼◻◻◼◼◻◻ (65)
◼◻◼◼◻◻◼◻◼◻ (66)
◼◻◼◼◻◻◼◻◻◼ (67)
◼◻◼◼◻◻◻◼◼◻ (68)
◼◻◼◼◻◻◻◼◻◼ (69)
◼◻◼◼◻◻◻◻◼◼ (70)
◼◻◼◻◼◼◼◻◻◻ (71)
◼◻◼◻◼◼◻◼◻◻ (72)
◼◻◼◻◼◼◻◻◼◻ (73)
◼◻◼◻◼◼◻◻◻◼ (74)
◼◻◼◻◼◻◼◼◻◻ (75)
◼◻◼◻◼◻◼◻◼◻ (76)
◼◻◼◻◼◻◼◻◻◼ (77)
◼◻◼◻◼◻◻◼◼◻ (78)
◼◻◼◻◼◻◻◼◻◼ (79)
◼◻◼◻◼◻◻◻◼◼ (80)
◼◻◼◻◻◼◼◼◻◻ (81)
◼◻◼◻◻◼◼◻◼◻ (82)
◼◻◼◻◻◼◼◻◻◼ (83)
◼◻◼◻◻◼◻◼◼◻ (84)
◼◻◼◻◻◼◻◼◻◼ (85)
◼◻◼◻◻◼◻◻◼◼ (86)
◼◻◼◻◻◻◼◼◼◻ (87)
◼◻◼◻◻◻◼◼◻◼ (88)
◼◻◼◻◻◻◼◻◼◼ (89)
◼◻◼◻◻◻◻◼◼◼ (90)
◼◻◻◼◼◼◼◻◻◻ (91)
◼◻◻◼◼◼◻◼◻◻ (92)
◼◻◻◼◼◼◻◻◼◻ (93)
◼◻◻◼◼◼◻◻◻◼ (94)
◼◻◻◼◼◻◼◼◻◻ (95)
◼◻◻◼◼◻◼◻◼◻ (96)
◼◻◻◼◼◻◼◻◻◼ (97)
◼◻◻◼◼◻◻◼◼◻ (98)
◼◻◻◼◼◻◻◼◻◼ (99)
◼◻◻◼◼◻◻◻◼◼ (100)
◼◻◻◼◻◼◼◼◻◻ (101)
◼◻◻◼◻◼◼◻◼◻ (102)
◼◻◻◼◻◼◼◻◻◼ (103)
◼◻◻◼◻◼◻◼◼◻ (104)
◼◻◻◼◻◼◻◼◻◼ (105)
◼◻◻◼◻◼◻◻◼◼ (106)
◼◻◻◼◻◻◼◼◼◻ (107)
◼◻◻◼◻◻◼◼◻◼ (108)
◼◻◻◼◻◻◼◻◼◼ (109)
◼◻◻◼◻◻◻◼◼◼ (110)
◼◻◻◻◼◼◼◼◻◻ (111)
◼◻◻◻◼◼◼◻◼◻ (112)
◼◻◻◻◼◼◼◻◻◼ (113)
◼◻◻◻◼◼◻◼◼◻ (114)
◼◻◻◻◼◼◻◼◻◼ (115)
◼◻◻◻◼◼◻◻◼◼ (116)
◼◻◻◻◼◻◼◼◼◻ (117)
◼◻◻◻◼◻◼◼◻◼ (118)
◼◻◻◻◼◻◼◻◼◼ (119)
◼◻◻◻◼◻◻◼◼◼ (120)
◼◻◻◻◻◼◼◼◼◻ (121)
◼◻◻◻◻◼◼◼◻◼ (122)
◼◻◻◻◻◼◼◻◼◼ (123)
◼◻◻◻◻◼◻◼◼◼ (124)
◼◻◻◻◻◻◼◼◼◼ (125)
◻◼◼◼◼◼◻◻◻◻ (126)
◻◼◼◼◼◻◼◻◻◻ (127)
◻◼◼◼◼◻◻◼◻◻ (128)
◻◼◼◼◼◻◻◻◼◻ (129)
◻◼◼◼◼◻◻◻◻◼ (130)
◻◼◼◼◻◼◼◻◻◻ (131)
◻◼◼◼◻◼◻◼◻◻ (132)
◻◼◼◼◻◼◻◻◼◻ (133)
◻◼◼◼◻◼◻◻◻◼ (134)
◻◼◼◼◻◻◼◼◻◻ (135)
◻◼◼◼◻◻◼◻◼◻ (136)
◻◼◼◼◻◻◼◻◻◼ (137)
◻◼◼◼◻◻◻◼◼◻ (138)
◻◼◼◼◻◻◻◼◻◼ (139)
◻◼◼◼◻◻◻◻◼◼ (140)
◻◼◼◻◼◼◼◻◻◻ (141)
◻◼◼◻◼◼◻◼◻◻ (142)
◻◼◼◻◼◼◻◻◼◻ (143)
◻◼◼◻◼◼◻◻◻◼ (144)
◻◼◼◻◼◻◼◼◻◻ (145)
◻◼◼◻◼◻◼◻◼◻ (146)
◻◼◼◻◼◻◼◻◻◼ (147)
◻◼◼◻◼◻◻◼◼◻ (148)
◻◼◼◻◼◻◻◼◻◼ (149)
◻◼◼◻◼◻◻◻◼◼ (150)
◻◼◼◻◻◼◼◼◻◻ (151)
◻◼◼◻◻◼◼◻◼◻ (152)
◻◼◼◻◻◼◼◻◻◼ (153)
◻◼◼◻◻◼◻◼◼◻ (154)
◻◼◼◻◻◼◻◼◻◼ (155)
◻◼◼◻◻◼◻◻◼◼ (156)
◻◼◼◻◻◻◼◼◼◻ (157)
◻◼◼◻◻◻◼◼◻◼ (158)
◻◼◼◻◻◻◼◻◼◼ (159)
◻◼◼◻◻◻◻◼◼◼ (160)
◻◼◻◼◼◼◼◻◻◻ (161)
◻◼◻◼◼◼◻◼◻◻ (162)
◻◼◻◼◼◼◻◻◼◻ (163)
◻◼◻◼◼◼◻◻◻◼ (164)
◻◼◻◼◼◻◼◼◻◻ (165)
◻◼◻◼◼◻◼◻◼◻ (166)
◻◼◻◼◼◻◼◻◻◼ (167)
◻◼◻◼◼◻◻◼◼◻ (168)
◻◼◻◼◼◻◻◼◻◼ (169)
◻◼◻◼◼◻◻◻◼◼ (170)
◻◼◻◼◻◼◼◼◻◻ (171)
◻◼◻◼◻◼◼◻◼◻ (172)
◻◼◻◼◻◼◼◻◻◼ (173)
◻◼◻◼◻◼◻◼◼◻ (174)
◻◼◻◼◻◼◻◼◻◼ (175)
◻◼◻◼◻◼◻◻◼◼ (176)
◻◼◻◼◻◻◼◼◼◻ (177)
◻◼◻◼◻◻◼◼◻◼ (178)
◻◼◻◼◻◻◼◻◼◼ (179)
◻◼◻◼◻◻◻◼◼◼ (180)
◻◼◻◻◼◼◼◼◻◻ (181)
◻◼◻◻◼◼◼◻◼◻ (182)
◻◼◻◻◼◼◼◻◻◼ (183)
◻◼◻◻◼◼◻◼◼◻ (184)
◻◼◻◻◼◼◻◼◻◼ (185)
◻◼◻◻◼◼◻◻◼◼ (186)
◻◼◻◻◼◻◼◼◼◻ (187)
◻◼◻◻◼◻◼◼◻◼ (188)
◻◼◻◻◼◻◼◻◼◼ (189)
◻◼◻◻◼◻◻◼◼◼ (190)
◻◼◻◻◻◼◼◼◼◻ (191)
◻◼◻◻◻◼◼◼◻◼ (192)
◻◼◻◻◻◼◼◻◼◼ (193)
◻◼◻◻◻◼◻◼◼◼ (194)
◻◼◻◻◻◻◼◼◼◼ (195)
◻◻◼◼◼◼◼◻◻◻ (196)
◻◻◼◼◼◼◻◼◻◻ (197)
◻◻◼◼◼◼◻◻◼◻ (198)
◻◻◼◼◼◼◻◻◻◼ (199)
◻◻◼◼◼◻◼◼◻◻ (200)
◻◻◼◼◼◻◼◻◼◻ (201)
◻◻◼◼◼◻◼◻◻◼ (202)
◻◻◼◼◼◻◻◼◼◻ (203)
◻◻◼◼◼◻◻◼◻◼ (204)
◻◻◼◼◼◻◻◻◼◼ (205)
◻◻◼◼◻◼◼◼◻◻ (206)
◻◻◼◼◻◼◼◻◼◻ (207)
◻◻◼◼◻◼◼◻◻◼ (208)
◻◻◼◼◻◼◻◼◼◻ (209)
◻◻◼◼◻◼◻◼◻◼ (210)
◻◻◼◼◻◼◻◻◼◼ (211)
◻◻◼◼◻◻◼◼◼◻ (212)
◻◻◼◼◻◻◼◼◻◼ (213)
◻◻◼◼◻◻◼◻◼◼ (214)
◻◻◼◼◻◻◻◼◼◼ (215)
◻◻◼◻◼◼◼◼◻◻ (216)
◻◻◼◻◼◼◼◻◼◻ (217)
◻◻◼◻◼◼◼◻◻◼ (218)
◻◻◼◻◼◼◻◼◼◻ (219)
◻◻◼◻◼◼◻◼◻◼ (220)
◻◻◼◻◼◼◻◻◼◼ (221)
◻◻◼◻◼◻◼◼◼◻ (222)
◻◻◼◻◼◻◼◼◻◼ (223)
◻◻◼◻◼◻◼◻◼◼ (224)
◻◻◼◻◼◻◻◼◼◼ (225)
◻◻◼◻◻◼◼◼◼◻ (226)
◻◻◼◻◻◼◼◼◻◼ (227)
◻◻◼◻◻◼◼◻◼◼ (228)
◻◻◼◻◻◼◻◼◼◼ (229)
◻◻◼◻◻◻◼◼◼◼ (230)
◻◻◻◼◼◼◼◼◻◻ (231)
◻◻◻◼◼◼◼◻◼◻ (232)
◻◻◻◼◼◼◼◻◻◼ (233)
◻◻◻◼◼◼◻◼◼◻ (234)
◻◻◻◼◼◼◻◼◻◼ (235)
◻◻◻◼◼◼◻◻◼◼ (236)
◻◻◻◼◼◻◼◼◼◻ (237)
◻◻◻◼◼◻◼◼◻◼ (238)
◻◻◻◼◼◻◼◻◼◼ (239)
◻◻◻◼◼◻◻◼◼◼ (240)
◻◻◻◼◻◼◼◼◼◻ (241)
◻◻◻◼◻◼◼◼◻◼ (242)
◻◻◻◼◻◼◼◻◼◼ (243)
◻◻◻◼◻◼◻◼◼◼ (244)
◻◻◻◼◻◻◼◼◼◼ (245)
◻◻◻◻◼◼◼◼◼◻ (246)
◻◻◻◻◼◼◼◼◻◼ (247)
◻◻◻◻◼◼◼◻◼◼ (248)
◻◻◻◻◼◼◻◼◼◼ (249)
◻◻◻◻◼◻◼◼◼◼ (250)
◻◻◻◻◻◼◼◼◼◼ (251)
(Finishes in 26 ms
on an old laptop.)
逻辑
基本步骤:
- 创建一个长度为m的索引数组,初始化为第一组合。
初始组合是由不同元素组成的组合数组,
- 在循环中,
- 增加最后一个索引(即m-1),直到n-1,
每次增加都会得到一组新的组合。
- 当最后一个索引变为n-1时,在循环中,
- 增加前面一个索引;
- 如果这两个索引相连,则将当前和上一个向左移动1位,然后继续增加,
每次增加都会得到一组新的组合;
- 否则,将相连的后缀移到与未连接的那一个后面,
移动后,将得到一组新的组合,
循环结束:
- 在增加前一个索引后,如果它的索引为0,并且是最高可能的值(即n-m),则完成;
特殊情况:
- 如果m = 1,则无需增加前一个索引,否则会导致超出索引范围(-1);
- 如果m = n,则只需要返回初始组合;
提示
E x E
的所有元素),所以我猜这只是术语问题。 - H WE^K
(或对于K = 2,写作ExE
)。 - H W