http://codeforces.com/problemset/problem/599/D
题意:
给出一个数x,问你有多少个n*m的网格中有x个正方形,输出n和m的值。
思路:
易得公式为:$sum_{i=0}^{n}(n-i)(m-i) $
化简得:$left [ n(n+1)-frac{n(n+1)}{2} ight ]*m+frac{n(n+1)(n+2)}{6}-frac{n(n+1)}{2}*n$
将n作为小的数,枚举n即可。
1 #include<iostream> 2 #include<cstdio> 3 #include<vector> 4 #include<cmath> 5 using namespace std; 6 7 typedef long long ll; 8 typedef pair<ll,ll> pll; 9 10 ll x; 11 vector<pll> ans1,ans2; 12 13 int main() 14 { 15 //freopen("in.txt","r",stdin); 16 ll tot = 0; 17 scanf("%lld",&x); 18 for(ll n=1;;n++) 19 { 20 ll a = n*(n+1) - n*(n+1)/2; 21 ll b = n*(n+1)*(2*n+1)/6 - n*n*(n+1)/2; 22 if(b > x) break; 23 if((x - b)%a == 0) 24 { 25 ll m = (x - b)/a; 26 if(m<n) continue; 27 ans1.push_back(make_pair(n,m)); 28 tot++; 29 if(m!=n) 30 { 31 ans2.push_back(make_pair(m,n)); 32 tot++; 33 } 34 } 35 } 36 printf("%lld ",tot); 37 for(int i=0;i<ans1.size();i++) 38 { 39 printf("%lld %lld ",ans1[i].first,ans1[i].second); 40 } 41 for(int i=ans2.size()-1;i>=0;i--) 42 { 43 printf("%lld %lld ",ans2[i].first,ans2[i].second); 44 } 45 return 0; 46 }