紀念郵票

http://www.yyycode.cn/index.php/2020/06/19/%e7%ba%aa%e5%bf%b5%e9%82%ae%e7%a5%a8/


Description

郵局最近推出一套郵票, 這套郵票共有n張,郵票面值各不相同,按編號順序爲1分,2分,3分...... 小航是一個集郵愛好者,他很喜歡這套郵票,可惜他現在身上只有M分,並不夠把全套都買下。他希望儘量買,最好剛好把所有的錢花光。作爲一個集郵愛好者,小航也不想買的編號斷斷續續。多義性小航打算買面值a分至b分的b-a+1張連續郵票,且總價剛好爲M 你的任務是求出所有符合條件的方案,以[a,b]的形式輸出。

Input

每個測試數據只有一行,包含兩個整數N,M(1 <= N, M <= 10^9)

Output

輸出所有的方案,按a重小到大輸出。 輸出文件不包含任何空格

Sample Input

20 15

Sample Output

[1,5]
[4,6]
[7,8]
[15,15]

思路:看到1e9,O(n)的做法是肯定卡的。估計是往log(n)或者sqrt(n)轉化。最開始是枚舉begin的,那我們轉化一下枚舉區間有多少個數。設區間的多少個數爲i;

由等差公式可以推 (begin+end)*i/2=M–>(begin+end)*i==2M;到這一步繼續轉化,(2*begin+i-1)*i==2M;這裏就可以看出來枚舉的i的範圍在sqrt(2M)內,然後就可以把枚舉的範圍縮小了

#include<iostream>
#include<vector>
#include<queue>
#include<cstring>
#include<cmath>
#include<algorithm>
using namespace std;
const int maxn=1e5;
typedef  long LL;

int main(void)
{
	LL N,M,begin,end;
	while(cin>>N>>M)
	{
		for(LL i=sqrt(2*M);i>=1;i--)//i->郵票張數
		{
			if(2*M%i==0&&((2*M/i)-i+1 )%2==0&&((2*M/i)-i+1)/2>=1&&((2*M/i)-i+1)/2+i-1<=N)
			{
				begin=((2*M/i)-i+1)/2;
				end=((2*M/i)-i+1)/2+i-1;
				cout<<"["<<begin<<","<<end<<"]"<<endl;
			}	
		} 
	}

return 0;
}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章