ExcelTip.Net留存知识帖 ---【注:附件之前被网盘供应商清空后,现已修复-现已修复-现已修复为本地下载!】
现在位置:首页 > E问E答 > Excel VBA > 如何按要求选数凑组合

如何按要求选数凑组合

作者:绿色风 分类: 时间:2022-08-17 浏览:226
楼主
芐雨
Q:如何按下面要求选数凑组合
1、在EXCEL中有三行数据,第一组A1——k1:1——11;第二组A2——k2:12——22;第三组A3——k3:23——33。
2、A4—C4由用户自由填入1~6的数字,要求A4+B4+C4=6。
3、D4和E4输入的数据要求为21<D4<E4<242。
4、分别从第一组取A4个数,第二组取B4个数,第三组取C4个数,形成6个数字组成的组合,并判断组合中的数相加是否大于D4小于E4格子的值,如果在此区间,则列出,如果不则忽略。如果一个组合都无法取得,则返回一个0。
问题引自百度:
  1. http://zhidao.baidu.com/question/262540180239919285.html?oldq=1
A:代码如下
  1. Sub Combin_芐雨()
  2.     Dim arr, ar(), brr(), crr()

  3.     '-------判断[A4:E4]是否适合要求------
  4.     For i = 1 To 3
  5.         If Cells(4, i) < 1 Or Cells(4, i) > 6 Or Cells(4, i) <> Int(Cells(4, i)) Then
  6.             MsgBox Cells(4, i).Address(0, 0) & "=" & Cells(4, i) & "不在[1,6]整数区间内": Exit Sub
  7.         End If
  8.     Next
  9.     If [A4] + [B4] + [C4] <> 6 Then
  10.         MsgBox "单元格[A4:C4]之和不等于6 ": Exit Sub
  11.     End If
  12.     If [D4] <= 21 Or [E4] >= 242 Or [D4] > [E4] Then
  13.         MsgBox "单元格[D4:E4]不符合要求(21<D4<E4<242) ": Exit Sub
  14.     End If

  15.     arr = Application.Transpose(Range("A1:K3"))
  16.     cb = Application.Transpose(Range("A4:C4"))
  17.     cb1 = Application.Combin(11, [A4])     '获取第一行的组合数
  18.     cb2 = Application.Combin(11, [B4])     '获取第二行的组合数
  19.     cb3 = Application.Combin(11, [C4])     '获取第二行的组合数
  20.     t1 = [D4]                              '区域最小值
  21.     t2 = [E4]                              '区域最大值
  22.     [O:IV].Clear                           '消除区域
  23.     cmax = Application.Max(cb1, cb2, cb3)    '三行组合数最大值

  24.     ReDim ar(1 To cmax, 1 To 6)        '六维数组;1-3维储存组合形式,4-6维储存组合之和
  25.     For i = 1 To 3                     '循环单元格[A4:C4]
  26.         x = 0
  27.         Select Case Cells(4, i)        '判断单元格[A4:C4]的值(因条件限制分别可能是:1,2,3,4)
  28.         Case 1                         '取1个数时
  29.             For x = 1 To 11
  30.                 ar(x, i) = arr(x, i)
  31.                 ar(x, i + 3) = arr(x, i)
  32.             Next
  33.         Case 2                        '取2个数时
  34.             For m = 1 To 11           '利用循环遍历所有组合,下同
  35.                 For n = m + 1 To 11
  36.                     x = x + 1         '记录数
  37.                     ar(x, i) = arr(m, i) & "+" & arr(n, i)    '组合形式
  38.                     ar(x, i + 3) = arr(m, i) + arr(n, i)      '组合之和
  39.                 Next
  40.             Next
  41.         Case 3                       '取3个数时,循环解释参考case2
  42.             For m = 1 To 9
  43.                 For n = m + 1 To 10
  44.                     For b = n + 1 To 11
  45.                         x = x + 1
  46.                         ar(x, i) = arr(m, i) & "+" & arr(n, i) & "+" & arr(b, i)
  47.                         ar(x, i + 3) = arr(m, i) + arr(n, i) + arr(b, i)
  48.                     Next
  49.                 Next
  50.             Next
  51.         Case 4                       '取4个数时,循环解释参考case2
  52.             For m = 1 To 8
  53.                 For n = m + 1 To 9
  54.                     For b = n + 1 To 10
  55.                         For c = b + 1 To 11
  56.                             x = x + 1
  57.                             ar(x, i) = arr(m, i) & "+" & arr(n, i) & "+" & arr(b, i) & "+" & arr(c, i)
  58.                             ar(x, i + 3) = arr(m, i) + arr(n, i) + arr(b, i) + arr(c, i)
  59.                         Next
  60.                     Next
  61.                 Next
  62.             Next
  63.         End Select
  64.     Next
  65.     n = cb1 * cb2 * cb3  '实际组合数
  66.     ReDim brr(1 To n, 1 To 2)
  67.     x = 0           '初始化
  68.     For i = 1 To cb1
  69.         For j = 1 To cb2
  70.             For k = 1 To cb3
  71.                 temp = ar(i, 4) + ar(j, 5) + ar(k, 6)
  72.                 If temp < t2 And temp > t1 Then   '组合之和是否在区域内的值
  73.                     x = x + 1
  74.                     brr(x, 1) = temp                           '组合之和
  75.                     brr(x, 2) = ar(i, 1) & "+" & ar(j, 2) & "+" & ar(k, 3) '组合形式
  76.                 End If
  77.             Next
  78.         Next
  79.     Next

  80.     Select Case x                    '判断适合条件的组合数
  81.     Case 0
  82.         MsgBox "没有合适条件的组合"
  83.     Case Is > Rows.Count             '若组合数大于列的最大值,转为多维数组
  84.         m = 1
  85.         n = 1
  86.         k = WorksheetFunction.RoundUp(x / Rows.Count, 0) * 2    ' 计算维数
  87.         ReDim crr(1 To Rows.Count, 1 To k)
  88.         For i = 1 To x
  89.             crr(m, n) = brr(i, 1)
  90.             crr(m, n + 1) = brr(i, 2)
  91.             If i Mod Rows.Count = 0 Then      '判断是否要转维
  92.                 m = 0: n = n + 2
  93.             End If
  94.             m = m + 1
  95.         Next
  96.         [O1].Resize(Rows.Count, k) = crr
  97.     Case Else
  98.         [O1].Resize(x, 2) = brr
  99.     End Select
  100.     [L7] = "组合数:"
  101.     [M7] = x
  102. End Sub

附件:
选数凑组合_芐雨.rar




2楼
gshshzr
不错
3楼
rongjun
感谢分享!
4楼
老糊涂
感谢分享

免责声明

有感于原ExcelTip.Net留存知识的价值及部分知识具有的时间限定性因素, 经与ExcelTip.Net站长Apolloh商议并征得其同意, 现将原属ExcelTip.Net的知识帖采集资料于本站点进行展示, 供有需要的人士查询使用,也慰缅曾经的论坛时代。 所示各个帖子的原作者如对版权有异议, 可与本人沟通提出,或于本站点留言,我们会尽快处理。 在此,感谢ExcelTip.Net站长Apolloh的支持,感谢本站点所有人**绿色风(QQ:79664738)**的支持与奉献,特此鸣谢!
------本人网名**KevinChengCW(QQ:1210618015)**原ExcelTip.Net总版主之一

评论列表
sitemap