POJ 3211Washing Clothes

只能说,无情的一题,比赛的时候看出来跟杭电的1171一样分成两部分01背包就可以了,但是WS的字符串深刻的暴露了我掉渣的C语言功底,不得不用map写,结果有个小小的地方没处理好,搞得样例过不了。。。最终队友看不下去,放下手正在推的公式,上去用字符串两WA两发后AC了。。。

我AC的代码:

#include <iostream>
#include<stdio.h>
#include<string>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<queue>
#include<map>
#define N 2222
using namespace std;

map<string,int>mp;
int sum[N];
int num[N];
int dp[N];
int f[15][N];
int main()
{
    int m,n;
    char str[N];
    while(~scanf("%d%d",&m,&n))
    {
        if(m+n==0)break;
        memset(num,0,sizeof num);
        memset(sum,0,sizeof sum);
        memset(dp,0,sizeof dp);
        int time;
        memset(f,0,sizeof f);
        for(int i=1;i<=m;i++)
        {
            scanf("%s",str);
            mp[str]=i;//存编号的数组
        }
        for(int i=1;i<=n;i++)
        {
            scanf("%d %s",&time,str);
            //cout<<mp[str]<<endl;
            sum[mp[str]]+=time;//记录某种颜色的总时间
            num[mp[str]]++;//记录某种颜色的总件数
            f[mp[str]][num[mp[str]]]=time;//编号为mp[str]的第j件衣服
        }
        int ans=0;
        for(int i=1;i<=m;i++)
        {
            int v=(sum[i]+1)/2;
            for(int j=1;j<=num[i];j++)
            for(int k=v;k>=f[i][j];k--)
            {
                dp[k]=max(dp[k],dp[k-f[i][j]]+f[i][j]);
            }
            ans+=max(dp[v],sum[i]-dp[v]);
            memset(dp,0,sizeof dp);//之前忘记清零了,wa了几下
        }
        printf("%d\n",ans);
    }
    return 0;
}

/*
2 6
blue red
2 red
8 red
3 blue
5 red
4 blue
6 red

3 7
blue red yy
2 red
8 red
3 blue
5 red
4 blue
6 red
3 yy
3 4
red blue yellow
2 red
3 blue
4 blue
6 red
0 0
*/

队友的代码:

#include <iostream>
#include<stdio.h>
#include<string>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<queue>
#include<map>
#define N 22220
using namespace std;

struct Node
{
    int t;
    string str;
}node[N];
int dp[N];
int cmp(Node a,Node b)
{
    return a.str>b.str;
}

int main()
{
    int m,n,i,j;
    char c[20];

    while(~scanf("%d%d",&m,&n))
    {
        if(n+m==0) break;
        for(int i=0;i<m;i++)
           scanf("%s",c);

        for(int i=0;i<n;i++)
        {
            scanf("%d",&node[i].t);
            cin>>node[i].str;

        }
        sort(node,node+n,cmp);
        int k=0;
        int a[N],sum;
        int ans=0;

        for(i=0;i<n;)
        {
           for(j=i;j<n;j++)
                if(node[j].str!=node[j+1].str)
                    break;

            k=0;sum=0;
           for(i;i<=j&&i<n;i++)
           {
               a[k++]=node[i].t;
               sum+=node[i].t;
           }

            memset(dp,0,sizeof(dp));

            int va=sum/2;

            for(int te=0;te<k;te++)
                for(int v=va;v>=a[te];v--)
                  dp[v]=max(dp[v-a[te]]+a[te],dp[v]);

            ans+=max(dp[va],sum-dp[va]);
        }

        printf("%d\n",ans);
    }
    return 0;
}

POJ 3211Washing Clothes

时间: 2024-10-25 22:26:37

POJ 3211Washing Clothes的相关文章

POJ Washing Clothes 洗衣服 (01背包,微变型)

题意:有多种颜色的衣服,由两个人合作来洗,必须洗完一种颜色才能洗下一种,求需要多少时间能洗完. 思路:将衣服按颜色分类,对每种颜色进行01背包,容量上限是该种颜色衣服全部洗完的耗时长一半,其实就是在最公平地平分工作量.因为一个先洗完就得等到另一人洗完.最后把洗完每种颜色的时长加起来返回.注:poj不允许用map,不然更省事,根据string和int做个哈希映射. 1 //#include <bits/stdc++.h> 2 #include <iostream> 3 #includ

POJ 3211 Washing Clothes 背包题解

本题是背包问题,但是需要转化成背包的. 因为是两个人洗衣服,那么就是说一个人只需要洗一半就可以了,因为不能两个人同时洗一件衣服,所以就成了01背包问题了. 思路: 1 计算洗完同一颜色的衣服需要的总时间totTime 2 利用动态规划背包法求这些衣服能在那些时间点完成 3 求比(totTime+1)/2大的最小时间点 4 得到洗一种颜色衣服的时间,那么继续求下洗一种颜色衣服的时间 5 最后加起来就是答案了. 这个是算法问题. 剩下来就是考编程功力了,因为给出的数据,需要我们自己把衣服分类,分类之

POJ 3211 Washing Clothes

Description Dearboy was so busy recently that now he has piles of clothes to wash. Luckily, he has a beautiful and hard-working girlfriend to help him. The clothes are in varieties of colors but each piece of them can be seen as of only one color. In

poj 3211 Washing Clothes 0-1背包

题意: 有2个人洗n件衣服,每件衣服有需要洗的时间和颜色,只能相同颜色的衣服两人一起洗,求洗完衣服的最少时间. 分析: 0-1背包判断某个重量是否能达到. 代码: //poj 3211 //sep9 #include <iostream> #include <map> #include <string> using namespace std; const int maxN=128; int m,n; map<string,int> name; int v[

Washing Clothes(poj 3211)

大体题意:有n件衣服,m种颜色,某人和他的女炮一起洗衣服,必须一种颜色洗完,才能洗另一种颜色,每件衣服都有时间,那个人洗都一样,问最少用时. poj万恶的C++和G++,害得我CE了三次 /* 背包啊……竟然有这么多玩法 不知道是不是被树形DP搞晕了,一上来就设了个三维数组,“f[i][j][0]代表前i件衣服, 时间差为j,且男生洗得多的时间”.搞了两个小时发现思路错了,这样会使两个背包毫无差别, 答案一定是错的. 正解:对于每种颜色,做一个01背包求方案树,加入j这个体积能填出来,那么另一个

[POJ 3211] Washing Clothes (动态规划)

题目链接:http://poj.org/problem?id=3211 题意:有M件衣服,每种衣服有一种颜色,一共有N种颜色.现在两个人洗衣服,规则是必须把这一种颜色的衣服全部洗完才能去洗下一种颜色的衣服. 问:在两个人可以同时洗衣服的情况下,把衣服全部洗完最少需要多久. 如果说两个人同时洗同一种颜色衣服,那么最少的时间就是洗完该颜色衣服的总时间的一半. 那么我们可以将洗每种衣服分开来看,视作一个01背包,容量是洗该颜色衣服的总时间的一半. 然后最多花多久.那么该颜色的总时间-这个人花的最多时间

POJ 3211 Washing Clothes(01背包)

http://poj.org/problem?id=3211 题意: 有m (1~10)种不同颜色的衣服总共n (1~100)件,Dearboy和她的girlfriend两个人要一起洗完全部衣服,为了预防色彩混合,他们每次只能同时洗同一种颜色的衣服,给出洗完每件衣服所需的时间time和它的颜色color,求出Dearboy和她的girlfriend最少用多少时间能洗完成全部衣服. 分析: 由于每种颜色的衣服是分开洗的, 所以我们可以把所有衣服按颜色分类, 然后每次看洗一种颜色的衣服最少需要花多少

POJ 3211 Washing Clothes【01背包】

题意:给出n种颜色,m件衣服,再分别给出m件衣服的颜色,和洗所需要的时间,dearboy和他的妹子一起洗衣服,且同种颜色的衣服不能同时洗,也不能两个人同时洗一件衣服,问洗完这m件衣服至少需要的时间 先考虑怎样才能让时间最少的方案,肯定是dearboy和他的妹纸各洗一半的时间,这样消耗的时间最少, 这样可以联想到杭电那一道big event in HDU,平均划分背包容量来做. 1 #include<iostream> 2 #include<cstdio> 3 #include<

POJ 3211 (分组01背包) Washing Clothes

题意: 小明有一个贤妻良母型的女朋友,他们两个一起洗衣服. 有M种颜色的N件衣服,要求洗完一种颜色的衣服才能洗另外一种颜色. 两人可以同时洗,一件衣服只能被一个人洗. 给出洗每件衣服所用的时间,求两个人洗完这些衣服所用的最短时间. 分析: 因为每种颜色是分开洗的,所以我们可以单独考虑一种颜色的衣服. 因为洗完这些衣服的总时间是固定的,所以两个人洗的时间尽可能的相等,这样洗完的时间最短. 所以将总时间的一半作为背包容量(这里总时间的奇偶性并不影响),物品的体积和价值都是洗每件衣服所用的时间,然后进