ZOJ - 4056 Press the Button 青島網路賽(思路)
阿新 • • 發佈:2018-11-04
題意
給你6個數,A,B,C,D,T,V,給你一盞燈,它每隔V+0.5秒就會熄滅,A表示的是你每隔A秒可以拍燈B 下,如果燈是滅的,我們就讓燈變亮,如果燈是亮的的話,我們就讓分數+1,並將燈重新設定為每隔V+0.5秒熄滅,問你T秒之後的得分是多少。
思路
首先我們可以算出在T秒中總共拍了多少次燈,他是
,怎麼的出來的?就是
秒中有多少個
就拍幾次,同理
也是,然後0秒的時候兩人同時拍是
。之後我們可以看出就是,他是有迴圈節的,每LCM之後就有一個迴圈,那麼我們得到一個迴圈節之後就能算出所有的了,現在的問題就是如何得到一個迴圈節的分數?首先我們篩出
和
的倍數,排序去重之後兩兩相減,如果差值大於
就表示我要浪費一次機會去把燈開啟,那麼我們最後就用總共拍了多少次燈-浪費的次數就能得到答案了
程式碼
#include <bits/stdc++.h>
using namespace std;
#define int long long
vector<long long>V;
signed main()
{
int T;
scanf("%lld",&T);
while(T--)
{
int a,b,c,d,v,t;
scanf("%lld%lld%lld%lld%lld%lld",&a,&b,&c,&d,&v,&t);
long long te = __gcd(a,c);
long long lcm = a*c/te;
V.clear();
for(int i = 0 ; i <= lcm ; i += a) V.push_back(i);
for(int i = 0 ; i <= lcm ; i += c) V.push_back(i);
sort(V.begin() , V.end());
V.erase(unique(V.begin() , V.end()) , V.end());
int tmp = 0;
for(int i = 1 ; i < V.size() ; i++)
{
if(V[i] - V[i-1] > v) tmp ++;
}
long long ans = (t/a) * b + (t/c) * d + b + d - 1;
long long cur = t/lcm;
ans = ans - cur*tmp;
long long la = t % lcm;
for(int i = 1 ; V[i] <= la ; i++)
{
if(V[i] - V[i-1] > v) ans --;
}
cout<<ans<<endl;
}
}