zoukankan      html  css  js  c++  java
  • 使用动态规划解决有关数字组合的问题

    题目:在SHEET2中列出SHEET1表中重量不超过170,体积不超过200的所有组合(http://club.excelhome.net/viewthread.php?tid=382466&page=1#pid2435030)

     

    Sheet1

    序号 重量 体积
    1 25 30
    2 26 31
    3 27 32
    4 28 33
    5 29 34
    6 30 35
    7 31 36
    8 32 37
    9 33 38
    10 34 39
    11 35 40
    12 36 41
    13 37 42
    14 38 43
    15 39 44
    16 40 45
    17 41 46
    18 42 47
    19 43 48
    20 44 49
    21 45 50
    22 46 51
    23 47 52
    24 48 53
    25 49 54
    26 50 55
    27 51 56
    28 52 57
    29 53 58
    30 54 59
    31 55 60
    32 56 61
    33 57 62
    34 58 63
    35 59 64
    36 60 65
    37 61 66
    38 62 67
    39 63 68
    40 64 69

    方法:动态规划,代码如下(可惜我的机子内存太小,无法定义更大的数组空间有效的完成此任务):

    Sub getit()
        Dim s() As String, i&, j&, k&, l&, n&, t, v, w, temp$, sum1&, sum2&
        t = Sheet1.[a2:c41]
        sum1 = 170
        sum2 = 200
        ReDim s(UBound(t), sum1, sum2)

        For i = 1 To UBound(t)
            If t(i, 2) <= sum1 And t(i, 3) <= sum2 Then s(1, t(i, 2), t(i, 3)) = t(i, 1)
        Next

        For j = 2 To UBound(t)
            For k = 1 To sum1
                For l = 1 To sum2
                    If s(j - 1, k, l) > "" Then
                        v = Split(s(j - 1, k, l))
                        For m = 0 To UBound(v)
                            If Not v(m) Like "*" & UBound(t) Then
                                w = Split(v(m), ",")
                                For i = Val(w(UBound(w))) + 1 To UBound(t)
                                    If k + t(i, 2) <= sum1 And l + t(i, 3) <= sum2 Then s(j, k + t(i, 2), l + t(i, 3)) = Trim(s(j, k + t(i, 2), l + t(i, 3)) & " " & v(m) & "," & t(i, 1))
                                Next
                            End If
                        Next
                    End If
                Next
            Next
        Next
        ReDim v(65535, 1 To 3)
        v(0, 1) = "序号"
        v(0, 2) = "重量"
        v(0, 3) = "体积"
        For k = 1 To sum1
            For l = 1 To sum2
                For j = 1 To UBound(t)
                    If s(j, k, l) > "" Then
                        w = Split(s(j, k, l))
                        For m = 0 To UBound(w)
                            n = n + 1
                            v(n, 1) = w(m)
                            v(n, 2) = k
                            v(n, 3) = l
                        Next
                    End If
                Next j, l, k
                Sheet2.[a1].Resize(n, 3) = v
            End Sub

     

    运行结果(返回54414组解):

     

     

    序号 重量 体积
    1 25 30
    2 26 31
    3 27 32
    4 28 33
    5 29 34
    6 30 35
    7 31 36
    8 32 37
    9 33 38
    10 34 39
    11 35 40
    12 36 41
    13 37 42
    14 38 43
    15 39 44
    16 40 45
    17 41 46
    18 42 47
    19 43 48
    20 44 49
    21 45 50
    22 46 51
    23 47 52
    24 48 53
    25 49 54
    26 50 55
    27 51 56
    1,2 51 61
    28 52 57
    1,3 52 62
    29 53 58
    1,4 53 63
    2,3 53 63
    30 54 59
    1,5 54 64
    2,4 54 64
    31 55 60
    1,6 55 65
    2,5 55 65
    3,4 55 65
    32 56 61
    1,7 56 66
    2,6 56 66
    3,5 56 66
    33 57 62
    1,8 57 67

    ................................

    6,8,9,13,14 170 195
    3,10,11,12,14 170 195
    4,9,11,12,14 170 195
    5,8,11,12,14 170 195
    6,7,11,12,14 170 195
    5,9,10,12,14 170 195
    6,8,10,12,14 170 195
    7,8,9,12,14 170 195
    6,9,10,11,14 170 195
    7,8,10,11,14 170 195
    4,10,11,12,13 170 195
    5,9,11,12,13 170 195
    6,8,11,12,13 170 195
    6,9,10,12,13 170 195
    7,8,10,12,13 170 195
    7,9,10,11,13 170 195
    8,9,10,11,12 170 195
    1,2,3,4,5,11 170 200
    1,2,3,4,6,10 170 200
    1,2,3,4,7,9 170 200
    1,2,3,5,6,9 170 200
    1,2,3,5,7,8 170 200
    1,2,4,5,6,8 170 200

  • 相关阅读:
    Microsoft 基准安全分析器(MBSA)
    神奇的C++模版
    Windows下的Memcache安装
    BisonFlex 笔记
    虚函数背后的秘密
    如何切换SecureCRT的帐号
    动态生成JS 实现 .NET 网站广告管理
    fatal error C1853 预编译头文件来自编译器的早期版本 解决方法
    解决 unresolved external symbol 无法解析 _send@16
    linux远程登录
  • 原文地址:https://www.cnblogs.com/fengju/p/6336238.html
Copyright © 2011-2022 走看看