POJ2100 Graveyard Design(尺取法)

POJ2100 Graveyard Design

  题目大意:给定一个数n,求出一段连续的正整数的平方和等于n的方案数,并输出这些方案,注意输出格式;

    循环判断条件可以适当剪支,提高效率,(1^2+2^2+..n^2)=n*(n+1)*(2n+1)/6;

    尺取时一定要注意循环终止条件的判断。

    

#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <ctime>
#include <iostream>
#include <algorithm>
#include <string>
#include <vector>
#include <deque>
#include <list>
#include <set>
#include <map>
#include <stack>
#include <queue>
#include <numeric>
#include <iomanip>
#include <bitset>
#include <sstream>
#include <fstream>
using namespace std;
#define rep(i,a,n) for (int i=a;i<n;i++)
#define per(i,a,n) for (int i=n-1;i>=a;i--)
#define in(n) scanf("%d",&(n))
#define in2(x1,x2) scanf("%d%d",&(x1),&(x2))
#define inll(n) scanf("%I64d",&(n))
#define inll2(x1,x2) scanf("%I64d%I64d",&(x1),&(x2))
#define inlld(n) scanf("%lld",&(n))
#define inlld2(x1,x2) scanf("%lld%lld",&(x1),&(x2))
#define inf(n) scanf("%f",&(n))
#define inf2(x1,x2) scanf("%f%f",&(x1),&(x2))
#define inlf(n) scanf("%lf",&(n))
#define inlf2(x1,x2) scanf("%lf%lf",&(x1),&(x2))
#define inc(str) scanf("%c",&(str))
#define ins(str) scanf("%s",(str))
#define out(x) printf("%d\n",(x))
#define out2(x1,x2) printf("%d %d\n",(x1),(x2))
#define outf(x) printf("%f\n",(x))
#define outlf(x) printf("%lf\n",(x))
#define outlf2(x1,x2) printf("%lf %lf\n",(x1),(x2));
#define outll(x) printf("%I64d\n",(x))
#define outlld(x) printf("%lld\n",(x))
#define outc(str) printf("%c\n",(str))
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define SZ(x) ((int)(x).size())
#define mem(X,Y) memset(X,Y,sizeof(X));
typedef vector<int> vec;
typedef long long ll;
typedef pair<int,int> P;
const int dx[4]={1,0,-1,0},dy[4]={0,1,0,-1};
const int INF=0x3f3f3f3f;
const ll mod=1e9+7;
ll powmod(ll a,ll b) {ll res=1;a%=mod;for(;b;b>>=1){if(b&1)res=res*a%mod;a=a*a%mod;}return res;}
const bool AC=true;

struct node{
    ll num,a,b;
};
node p[100000];
bool cmp(node x,node y){
    return x.num>y.num;
}
int main(){
    ll n,s,t,sum,k,cnt;//都设为longlong免得溢出
    while(inll(n)!=EOF){
        s=t=1;sum=0;k=0;
        while(true){
            while(sum<n){  //注意循环终止条件
                sum+=t*t;
                t++;
            }
            if(sum==n) {
                p[k].num=t-s;
                p[k].a=s;
                p[k++].b=t-1;
            }
            sum-=s*s;
            s++;
            if(s*s>n) break; //注意循环终止条件
        }
        cnt=k;
        printf("%I64d\n",cnt);//别忘了这个
        sort(p,p+k,cmp);
        rep(i,0,k){
            printf("%I64d ",p[i].num);
            for(ll j=p[i].a;j<=p[i].b;j++){
                printf("%I64d ",j);
            }
            printf("\n");
        }
    }
    return 0;
}
时间: 2024-10-09 03:06:55

POJ2100 Graveyard Design(尺取法)的相关文章

poj 2100 Graveyard Design(尺取法)

Description King George has recently decided that he would like to have a new design for the royal graveyard. The graveyard must consist of several sections, each of which must be a square of graves. All sections must have different number of graves.

poj2100(尺取法)

题意:选取一系列数,使得这些数的平方和等于n: 解题思路:尺取法扫一遍: #include<iostream> #include<algorithm> using namespace std; struct node { int bin; int len; }a[1000005]; int main() { long long right=1,left=1,cnt=0; long long sum=0,n; cin>>n; while(1) { while(sum<

poj 2100(尺取法)

Graveyard Design Time Limit: 10000MS   Memory Limit: 64000K Total Submissions: 6107   Accepted: 1444 Case Time Limit: 2000MS Description King George has recently decided that he would like to have a new design for the royal graveyard. The graveyard m

poj 2100 Graveyard Design

Graveyard Design Time Limit: 10000MS   Memory Limit: 64000K Total Submissions: 7357   Accepted: 1816 Case Time Limit: 2000MS Description King George has recently decided that he would like to have a new design for the royal graveyard. The graveyard m

尺取法 TwoPoint

就是两个指针表示区间[l,r]的开始与结束然后根据题目来将端点移动,是一种十分有效的做法.适合连续区间的问题 3320 这道意思是一本书有n页,每一页上有一个知识点标号a[i]可能重复,要求选择一个最小的区间使得能够覆盖所有知识点 分析:[l,r]区间推进,统计区间中能够覆盖的知识点数,对于每一个l,r都是满足可以覆盖所有知识点的最小r,处理好区间知识点数的统计就好了 1 #include <iostream> 2 #include <cstdio> 3 #include <

luogu 1712 区间(线段树+尺取法)

题意:给出n个区间,求选择一些区间,使得一个点被覆盖的次数超过m次,最小的花费.花费指的是选择的区间中最大长度减去最小长度. 坐标值这么大,n比较小,显然需要离散化,需要一个技巧,把区间转化为半开半闭区间,然后线段树的每一个节点表示一个半开半闭区间. 接着我们注意到需要求最小的花费,且这个花费只与选择的区间集合中的最大长度和最小长度有关. 这意味着如果最大长度和最小长度一定,我们显然是需要把中间长度的区间尽量的选择进去使答案不会变的更劣. 不妨把区间按长度排序,枚举每个最小长度区间,然后最大区间

poj 3320 Jessica&#39;s Reading Problem(尺取法+map/hash)

题目:http://poj.org/problem?id=3320 题意:给定N个元素的数组,找出最短的一段区间使得区间里面的元素种类等于整个数组的元素种类. 分析:暴力枚举区间的起点x,然后找到最小的y,使得区间[x,y]满足条件,x向有移位后变成x',现在的y'肯定不至于在y的左边.存状态的话map和hash都可以. map代码: #include <iostream> #include <set> #include <map> #include <cstdi

hihocoder-1483区间价值 (二分+尺取法)

题目链接: 区间价值 给定n个数A1...An,小Ho想了解AL..AR中有多少对元素值相同.小Ho把这个数目定义为区间[L,R]的价值,用v[L,R]表示. 例如1 1 1 2 2这五个数所组成的区间的价值为4. 现在小Ho想知道在所有的的v[L,R](1 <= L <= R <= n)中,第k小的值是多少. Input 第一行一个数T(T<=10),表示数据组数. 对于每一组数据: 第一行两个数n,k(1<=n<=200,000,1<=k<=n*(n+1

【转】毛虫算法&mdash;&mdash;尺取法

转自http://www.myexception.cn/program/1839999.html 妹子满分~~~~ 毛毛虫算法--尺取法 有这么一类问题,需要在给的一组数据中找到不大于某一个上限的"最优连续子序列" 于是就有了这样一种方法,找这个子序列的过程很像毛毛虫爬行方式,我管它叫毛毛虫算法,比较流行的叫法是"尺取法". 喏,就像图里的妹纸一样~ 还是举个栗子: Poj3061 给长度为n的数组和一个整数m,求总和不小于m的连续子序列的最小长度 输入 n = 1