zoukankan      html  css  js  c++  java
  • 2020牛客暑期多校训练营(第七场)A-Social Distancing dp打表

    A- Social Distancing

    题意

    你要在半径为(r),圆心为((0,0))的圆上找(n)个整数点,使得每对点的距离平方和最小。

    [sum_{i=1}^{n-1}sum_{j=i+1}^{n}d(i,j)^2 ]

    分析

    考虑(dp)打表,状态(dp[i][j][k])为放置了(i)个点,横坐标和为(j),纵坐标和为(k)的每个点和圆心的距离的平方和的最大值,为什么这样(dp)

    把题目中的公式化简一下

    [sum_{i=1}^{n-1}sum_{j=i+1}^{n}(x_i-x_j)^2+(y_i-y_j)^2 \ =sum_{i=1}^{n-1}sum_{j=i+1}^{n}x_i^2+x_j^2+y_i^2+y_j^2-2x_ix_j-2y_iy_j \ =(sum_{i=1}^{n}n(x_i^2+y_i^2))-(sum_{i=1}^{n}x_i)^2-(sum_{i=1}^{n}y_i)^2 \ =n imes dp[n][j][k]-j^2-k^2 ]

    维护第一项的值,枚举(j,k)去更新(dp)值,用数组(ans[i][r])来更新在半径为(r)的圆,放置了(i)个点的答案,(ans[i][r]=max {i imes dp[i][j][k]-j^2-k^2 })

    打表Code

    #include<algorithm>
    #include<iostream>
    #include<cstring>
    #include<iomanip>
    #include<sstream>
    #include<cstdio>
    #include<string>
    #include<vector>
    #include<bitset>
    #include<queue>
    #include<cmath>
    #include<stack>
    #include<set>
    #include<map>
    #define rep(i,x,n) for(int i=x;i<=n;i++)
    #define per(i,n,x) for(int i=n;i>=x;i--)
    #define sz(a) int(a.size())
    #define rson mid+1,r,p<<1|1
    #define pii pair<int,int>
    #define lson l,mid,p<<1
    #define ll long long
    #define pb push_back
    #define mp make_pair
    #define se second
    #define fi first
    using namespace std;
    const double eps=1e-8;
    const int mod=1e9+7;
    const int N=1e5+10;
    const int inf=1e9;
    const int base=303;
    int dp[11][610][610];
    int ans[11][33];
    vector<pii>q;
    int main(){
    	//ios::sync_with_stdio(false);
    	//freopen("in","r",stdin);
    	rep(i,-30,30){
    		rep(j,-30,30){
    			if(i*i+j*j<=30*30){
    				q.pb(mp(i,j));
    			}
    		}
    	}
    	sort(q.begin(), q.end(),[](pii x,pii y){return x.fi*x.fi+x.se*x.se<y.fi*y.fi+y.se*y.se;});
    	memset(dp,-1,sizeof(dp));
    	dp[0][base][base]=0;
    	int now=0;
    	for(int r=1;r<=30;r++){
    		for(;now<sz(q);++now){
    			pii x=q[now];
    			if(x.fi*x.fi+x.se*x.se>r*r) break;
    			for(int i=1;i<=8;i++){
    				for(int j=base-r*i;j<=base+r*i;j++) {
    					for(int k=base-r*i;k<=base+r*i;k++) if(~dp[i-1][j-x.fi][k-x.se]){
    						dp[i][j][k]=max(dp[i][j][k],dp[i-1][j-x.fi][k-x.se]+(x.fi*x.fi+x.se*x.se));
    					}
    				}
    			}
    		}
    		rep(i,1,8) rep(j,base-r*i,base+r*i) rep(k,base-r*i,base+r*i) if(~dp[i][j][k]){
    			int t1=j-base,t2=k-base;
    			ans[i][r]=max(ans[i][r],i*dp[i][j][k]-t1*t1-t2*t2);
    		}
    	}
    	rep(i,1,8) rep(j,1,30){
    		cout<<ans[i][j]<<',';
    		if(j==30) cout<<'
    ';
    	}
    	return 0;
    }
    

    Code

    #include<algorithm>
    #include<iostream>
    #include<cstring>
    #include<iomanip>
    #include<sstream>
    #include<cstdio>
    #include<string>
    #include<vector>
    #include<bitset>
    #include<queue>
    #include<cmath>
    #include<stack>
    #include<set>
    #include<map>
    #define rep(i,x,n) for(int i=x;i<=n;i++)
    #define per(i,n,x) for(int i=n;i>=x;i--)
    #define sz(a) int(a.size())
    #define rson mid+1,r,p<<1|1
    #define pii pair<int,int>
    #define lson l,mid,p<<1
    #define ll long long
    #define pb push_back
    #define mp make_pair
    #define se second
    #define fi first
    using namespace std;
    const double eps=1e-8;
    const int mod=1e9+7;
    const int N=1e5+10;
    const int inf=1e9;
    int T,n,r;
    int a[8][30]={
    0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
    4,16,36,64,100,144,196,256,324,400,484,576,676,784,900,1024,1156,1296,1444,1600,1764,1936,2116,2304,2500,2704,2916,3136,3364,3600,
    8,32,76,130,224,312,416,554,722,896,1064,1248,1512,1746,2016,2264,2600,2888,3218,3584,3912,4344,4712,5138,5612,6062,6536,6984,7520,8084,
    16,64,144,256,400,576,784,1024,1296,1600,1936,2304,2704,3136,3600,4096,4624,5184,5776,6400,7056,7744,8464,9216,10000,10816,11664,12544,13456,14400,
    24,96,218,384,624,880,1188,1572,2014,2496,2984,3520,4224,4870,5616,6336,7224,8056,9008,9984,10942,12080,13144,14326,15624,16896,18184,19488,20968,22480,
    36,144,324,576,900,1296,1764,2304,2916,3600,4356,5184,6084,7056,8100,9216,10404,11664,12996,14400,15876,17424,19044,20736,22500,24336,26244,28224,30276,32400,
    48,192,432,768,1224,1740,2356,3102,3954,4896,5872,6960,8280,9564,11016,12456,14160,15816,17666,19584,21500,23688,25808,28122,30624,33120,35664,38266,41200,44076,
    64,256,576,1024,1600,2304,3136,4096,5184,6400,7744,9216,10816,12544,14400,16384,18496,20736,23104,25600,28224,30976,33856,36864,40000,43264,46656,50176,53824,57600
    };
    int main(){
        //ios::sync_with_stdio(false);
        //freopen("in","r",stdin);
        cin>>T;
        while(T--){
            cin>>n>>r;
            cout<<a[n-1][r-1]<<endl;
        }
        return 0;
    }
    
  • 相关阅读:
    JS在ff和ie区别(未完,待续...)
    得出一年中已过的天数
    div高度随浏览器变化
    offsetTop,offsetLeft
    完美的DIV三行三列自适应高度布局
    YUI Compressor
    Android repo 出现error.GitError: manifests revlist ('^12303f87b9f90c07bf4aec4c4353ba514ee70c8a', 'HEAD', ''): fatal: bad revision 'HEAD'
    1、ECharts(中国地图篇)的使用
    2012年新浪微博用户密码泄露漏洞(图片解析)
    铁道部购票网站可能造成另一次的密码危机(转)
  • 原文地址:https://www.cnblogs.com/xyq0220/p/13418747.html
Copyright © 2011-2022 走看看