zoj 2068 - Chopsticks

题目:非常多人在一起吃饭。有两组单支的筷子,定义badness为一对筷子长度差的平方,求最小的badness和。

分析:dp,最大公共子序列类似物。

这里利用数学关系找到一个结论:

a < b < c < d 时,(c - a)^2 +(d-b)^2 <(d-a^2)+(c-b)^2;(展开就可以)

所以最优解一定不会交叉,然后先用元素少的串,求长串的LCS的就可以。

权值计算用长度差的平方,而不是1。

这里,能够设置两种状态f(i。j):

1.以a[i]。b[j]为结束标志的最优解,则 T(n)= n^3    { 须要遍历前一位置,非常多反复 };

2.a[1..i]与b[1..j]两区间的最优解,则T(n)= n^2   { 仅仅取决本位置选否,去掉反复 }。

说明:(2011-09-24 05:03)。

#include <stdio.h>
#include <stdlib.h>

#define min( a, b ) ((a)<(b)?(a):(b))

int A[ 501 ];
int B[ 501 ];
int T[ 501 ][ 501 ];
int S[ 501 ][ 501 ];

int cmp( const void*a, const void*b )
{
    return *((int *)a) - *((int *)b);
}

int f( int *a, int *b, int N, int M )
{
    for ( int i = 1 ; i <= N ; ++ i )
    for ( int j = i ; j <= M ; ++ j )
        S[ i ][ j ] = (a[ i ]-b[ j ])*(a[ i ]-b[ j ]);
    for ( int i = 1 ; i <= N ; ++ i )
    for ( int j = i ; j <= M ; ++ j )
        T[ i ][ j ] = 0xfffffff;
    for ( int i = 0 ; i <= M ; ++ i )
        T[ 0 ][ i ] = 0;
    for ( int i = 1 ; i <= N ; ++ i ) {
        T[ i ][ i ] = T[ i-1 ][ i-1 ] + S[ i ][ i ];
        for ( int j = i+1 ; j <= M ; ++ j )
            T[ i ][ j ] = min( T[ i-1 ][ j-1 ]+S[ i ][ j ], T[ i ][ j-1 ] );
    }

    return T[ N ][ M ];
}

int main()
{
    int t,N,M,S;
    scanf("%d",&t);
    while ( t -- ) {
        scanf("%d",&N);
        for ( int i = 1 ; i <= N ; ++ i )
            scanf("%d",&A[ i ]);
        scanf("%d",&M);
        for ( int i = 1 ; i <= M ; ++ i )
            scanf("%d",&B[ i ]);
        qsort( &A[ 1 ], N, sizeof( int ), cmp );
        qsort( &B[ 1 ], M, sizeof( int ), cmp );

        if ( N <= M )
            printf("%d\n",f( A, B, N, M ));
        else
            printf("%d\n",f( B, A, M, N ));
    }
    return 0;
}
时间: 2024-10-12 03:20:20

zoj 2068 - Chopsticks的相关文章

zoj题目分类

饮水思源---zoj 转载自:http://bbs.sjtu.edu.cn/bbscon,board,ACMICPC,file,M.1084159773.A.html 注:所有不是太难的题都被归成了“简单题”,等到发现的时候已经太晚了,我太死脑筋 了……:( 有些题的程序我找不到了,555……:( SRbGa的题虽然都很经典……但是由于其中的大部分都是我看了oibh上的解题报告后做 的,所以就不写了…… 题目排列顺序没有规律……:( 按照个人感觉,最短路有的算做了DP,有的算做了图论. 有些比较

概率dp ZOJ 3640

Help Me Escape Time Limit:2000MS     Memory Limit:32768KB     64bit IO Format:%lld & %llu Submit Status Practice ZOJ 3640 Appoint description:  System Crawler  (2014-10-22) Description Background     If thou doest well, shalt thou not be accepted? an

zoj 2156 - Charlie&#39;s Change

题目:钱数拼凑,面值为1,5,10,25,求组成n面值的最大钱币数. 分析:dp,01背包.需要进行二进制拆分,否则TLE,利用数组记录每种硬币的个数,方便更新. 写了一个 多重背包的 O(NV)反而没有拆分快.囧,最后利用了状态压缩优化 90ms: 把 1 cents 的最后处理,其他都除以5,状态就少了5倍了. 说明:貌似我的比大黄的快.(2011-09-26 12:49). #include <stdio.h> #include <stdlib.h> #include <

ZOJ 1718 POJ 2031 Building a Space Station 修建空间站 最小生成树 Kruskal算法

题目链接:ZOJ 1718 POJ 2031 Building a Space Station 修建空间站 Building a Space Station Time Limit: 2 Seconds      Memory Limit: 65536 KB You are a member of the space station engineering team, and are assigned a task in the construction process of the statio

ZOJ 3607 Lazier Salesgirl (贪心)

Lazier Salesgirl Time Limit: 2 Seconds      Memory Limit: 65536 KB Kochiya Sanae is a lazy girl who makes and sells bread. She is an expert at bread making and selling. She can sell the i-th customer a piece of bread for price pi. But she is so lazy

ZOJ - 2243 - Binary Search Heap Construction

先上题目: Binary Search Heap Construction Time Limit: 5 Seconds      Memory Limit: 32768 KB Read the statement of problem G for the definitions concerning trees. In the following we define the basic terminology of heaps. A heap is a tree whose internal n

ZOJ 2859 二维线段树

思路:自己写的第二发二维线段树1A,哈哈,看来对二维的push操作比较了解了:但是还没遇到在两个线段树中同时进行push操作的,其实这题我是想在x维和y维同时进行push操作的,但是想了好久不会,然后看到这题又给出10秒,然后想想在x维线段直接单点查询肯定也过了,然后在第二维就只有pushup操作,在第一维线段树没有pushup操作.要是在第一维也有pushup操作的话,那就不用单点查询那么慢了.不过也A了,想找题即在二维同时进行pushup和pushdown操作的. #include<iost

ZOJ 2588

求一个无向图的桥(可能存在重边),输出割边的数目,并按顺序输出割边的序号(输入的顺序). 由于内存的限制 , 无法使用邻接矩阵 , 只能用邻接表了 . 第一次用了邻接表,超内存了: 1 #include <iostream> 2 #include <cstdio> 3 #include <algorithm> 4 #include <string.h> 5 using namespace std; 6 const int N=10002; 7 const i

ZOJ 2587 Unique Attack 判断最小割是否唯一

很裸的判断最小割是否唯一.判断方法是先做一遍最大流求最小割,然后从源点和汇点分别遍历所有能够到达的点,看是否覆盖了所有的点,如果覆盖了所有的点,那就是唯一的,否则就是不唯一的. #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <climits> #include <string> #include <iostr