在寝室睡了几天以后过来做 自闭了
题意 给你t组样例 一个区间 l 到 r ,让你输出 l 到 r 内一对其中一个是另一个的因子的答案 , 保证题目有解
于是我们直接输出左端点 和左端点乘2 即可 保证是最小的答案
#include <cstdio>
#include <queue>
#include <cmath>
#include <cstring>
#include <iostream>
#include <stack>
#include <set>
#include <sstream>
#include <vector>
#include <algorithm>
using namespace std;
#define dbg(x) cout<<#x<<" = "<< (x)<< endl
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
long long a,b;
scanf("%lld%lld",&a,&b);
printf("%lld %lld\n",a,a*2);
}
return 0;
}
题意 给你一个长度为n的字符串 你可以删掉任意长度的子串(包括n) 使得剩下的串都是同一个字符 或者 没有字符(删掉n)
我们可以分类讨论一下会发现几种类型的删除方法
abaa 和 abcc 和 aaaa
可以模拟一下 就可以写了
#include <cstdio>
#include <queue>
#include <cmath>
#include <cstring>
#include <iostream>
#include <stack>
#include <set>
#include <sstream>
#include <vector>
#include <algorithm>
using namespace std;
#define dbg(x) cout<<#x<<" = "<< (x)<< endl
#define MOD 998244353
char str[200025];
int main()
{
bool flag = false;
long long n,tmp = 1,tmp_,len = 1,ans = 0;
scanf("%lld",&n);
tmp_ = n;
scanf("%s",str+1);
if(str[n]==str[1]) flag = true;
while(str[tmp]==str[tmp+1]&&tmp<n)
{
tmp++;
}
while(str[tmp_]==str[tmp_-1]&&tmp_>1)
{
tmp_--;
len++;
}
if(tmp==n)
{
printf("%lld\n",(n*(n+1)/2)%MOD);
return 0;
}
if(flag)
{
while(tmp--)
{
ans+=len+1;
}
ans+=len+1;
printf("%lld\n",ans%MOD);
}
else printf("%lld\n",(len+tmp+1)%MOD);
return 0;
}
题意 给你 t 组样例,问你每个样例的角度可以由 正x边形凑成 输出最小的x
我们知道正多边形 外接一个圆 所以同弦的圆周角相同 也就是说 内角和为 (x-2)*180 ,每个内角为 (x-2)*180 / x,每个内角可以等分(x-2)段 即小单元为 180/x
于是就可以模拟了 可以用乘法代替出发 也可以直接用fmod
#include <cstdio>
#include <queue>
#include <cmath>
#include <cstring>
#include <iostream>
#include <stack>
#include <set>
#include <sstream>
#include <vector>
#include <algorithm>
using namespace std;
#define dbg(x) cout<<#x<<" = "<< (x)<< endl
vector <pair<double ,int > > arr;
int main()
{
int t;
scanf("%d",&t);
for(int i = 3;i<=15500;i++)
{
arr.push_back(make_pair(1.0*180/i,i));
}
while(t--)
{
int n;
scanf("%d",&n);
/*if(n&1)
{
printf("-1\n");
continue;
}*/
int sz = arr.size();
int flag = 0;
for(int i = 0;i<sz;++i)
{
if(fmod(1.0*n,arr[i].first)==0&&((arr[i].second-2)*arr[i].first>=n))
{
flag = 1;
printf("%d\n",arr[i].second);
break;
}
}
if(!flag) printf("-1\n");
}
return 0;
}
题意 我们定义一个串里面如果按顺序出现 h a r d 那么就是h a r d 串 要求你删除任意字符 使得不存在h a r d 串
做法:我们知道要是不想要hard 就可以删除掉 h 使得 hard不存在 ,或者删除掉ha使得hard不存在,或者删除掉har使得hard不存在 或者删除掉hard使得hard不存在
我们知道 当一个最小的删除h使得hard不存在 可能要删除多个h 但是删除a的时候可以由之前删除了一个h再删除一个a即可 不需要多次删除
所以我们定义一个四个状态的dp fa[0][i]代表 i 长度前面的h都被删除需要的代价 同理 dp[1][i]代表 i 长度前面的ha都被删除所需要的代价,dp[2][i] 代表 i 长度前面的har 都被删除所需要的代价 , dp[3][i] 代表 i 长度前面的hard 都被删除所需要的代价
#include <cstdio>
#include <queue>
#include <cmath>
#include <cstring>
#include <iostream>
#include <stack>
#include <set>
#include <sstream>
#include <vector>
#include <algorithm>
using namespace std;
#define dbg(x) cout<<#x<<" = "<< (x)<< endl
#define MOD 998244353
const int MAX_N = 100025;
long long fa[4][MAX_N],a[MAX_N];
char str[MAX_N];
int main()
{
int n;
scanf("%d",&n);
scanf("%s",str+1);
for(int i = 1;i<=n;++i) scanf("%lld",&a[i]);
for(int i = 1;i<=n;++i)
{
fa[0][i] = fa[0][i-1]+a[i]*(str[i]=='h');
fa[1][i] = min(fa[0][i],fa[1][i-1]+a[i]*(str[i]=='a'));
fa[2][i] = min(fa[1][i],fa[2][i-1]+a[i]*(str[i]=='r'));
fa[3][i] = min(fa[2][i],fa[3][i-1]+a[i]*(str[i]=='d'));
}
printf("%lld\n",min(min(fa[0][n],fa[1][n]),min(fa[2][n],fa[3][n])));
return 0;
}