• GarsiaWachs算法


    对于一列的石子归并问题,除了朴素的O(n^3)的dp做法及其O(n^2)优化,还有GarsiaWachs算法。

    算法流程是,找一个最小的k,使得a[k-1]<=a[k+1],将a[k-1]和a[k]合并;从当前位置向前找到一个最大的i,使得a[i]>a[k-1]+a[k],并将新合并的一堆移到i的后面;重复操作n-1次,直至只剩下1堆,答案就是每次合并结果累加起来。

     1 #include <cstdio>
     2 
     3 const int maxn = 105, inf = 0x3f3f3f3f;
     4 
     5 struct Node {
     6     int num, pre, next;
     7 } a[maxn];
     8 
     9 inline void del(int x) {
    10     int pp = a[a[x].pre].pre, nn = a[x].next;
    11     a[pp].next = nn, a[nn].pre = pp;
    12 }
    13 
    14 inline void insert(int x, int y) {
    15     a[x].pre = y, a[x].next = a[y].next;
    16     a[a[y].next].pre = x, a[y].next = x;
    17 }
    18 
    19 int main() {
    20     int n, ans = 0;
    21     scanf("%d", &n);
    22     a[0].num = a[n + 1].num = inf;
    23     a[0].next = 1, a[n + 1].pre = n;
    24     for (int i = 1; i <= n; ++i) {
    25         scanf("%d", &a[i].num);
    26         a[i].pre = i - 1, a[i].next = i + 1;
    27     }
    28     for (int t = 1; t <= n - 1; ++t) {
    29         int x, y, sum;
    30         for (int i = a[0].next; ; i = a[i].next)
    31             if (a[a[i].pre].num <= a[a[i].next].num) {
    32                 x = i;
    33                 break;
    34             }
    35         sum = a[a[x].pre].num + a[x].num;
    36         for (int i = a[a[x].pre].pre; ; i = a[i].pre)
    37             if (a[i].num > sum) {
    38                 y = i;
    39                 break;
    40             }
    41         del(x);
    42         a[x].num = sum;
    43         printf("%d ttt
    ", sum);
    44         insert(x, y);
    45         ans += sum;
    46     }
    47     printf("%d", ans);
    48     return 0;
    49 }
    Code Example
  • 相关阅读:
    shell cut
    查询表名
    RandomAccessFile
    eclipse 背景颜色
    JAVA 获取分行符
    date time insert
    shell date time
    python
    gdg shell
    shell入门之变量测试
  • 原文地址:https://www.cnblogs.com/Mr94Kevin/p/10926709.html
Copyright © 2020-2023  润新知