1001:Maximum Multiple
思路:根据题意,设,易推导出来
,这样
的取值范围就只有有限的3,3,3和2,4,4和2,3,6这三种取法,并且2,3,6是不如前两种取法,所以答案就是
。
代码:
#include<bits/stdc++.h>
using namespace std;
int main()
{
int t;scanf("%d",&t);
while(t--){
long long n;scanf("%lld",&n);
if(n%3==0)printf("%lld\n",n*n*n/27);
else if(n%4==0)printf("%lld\n",n*n*n/32);
else printf("-1\n");
}
}
1002:Balanced Sequence
思路:谜之排序。。。正确的排序应该是先分类(左括号多还是右括号多),然后对同一类的在比较(左括号多的,比较右括号少的放前面;右括号多的,比较左括号少的放前面)。
代码:
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e5+10;
struct node{
int a,b;
bool operator < (const node & p)const {
if(b>=a && p.b<p.a)return false;
if(b<a && p.b>=p.a)return true;
if(b>=a && p.b>=p.a)return a>p.a;
return b<p.b;
}
};
vector<node>v;
char s[maxn];int ans=0;
void solve()
{
int len=strlen(s);int ll=0,rr=0;
for(int i=0;i<len;i++){
if(s[i]=='(')ll++;
if(s[i]==')'){
if(ll!=0){
ll--;ans+=2;
}
else rr++;
}
}
v.push_back((node){ll,rr});
}
int main()
{
//freopen("1002.in","r",stdin);
//freopen("1002me.out","w",stdout);
int t;scanf("%d",&t);
while(t--){
int n;scanf("%d",&n);v.clear();ans=0;
for(int i=1;i<=n;i++){
scanf("%s",s);solve();
}
sort(v.begin(),v.end());
int left=0,right=0;
for(int i=0;i<n;i++){
int k=min(left,v[i].b);ans+=k*2;
left=left+v[i].a-k;
right=right+v[i].b-k;
}
printf("%d\n",ans);
}
}
1003:Triangle Partition
思路:先按x排序,再按y排序,然后依次每三个点输出一行。
代码:
#include<bits/stdc++.h>
using namespace std;
struct node
{
int x,y,id;
bool operator < (const node & a)const {
return x==a.x?y<a.y:x<a.x;
}
};
vector<node>v;
int main()
{
int t;scanf("%d",&t);
while(t--){
int n;scanf("%d",&n);v.clear();
for(int i=1;i<=n*3;i++){
int x,y;scanf("%d%d",&x,&y);
v.push_back((node){x,y,i});
}
sort(v.begin(),v.end());
for(int i=1;i<=n;i++){
printf("%d %d %d\n",v[(i-1)*3].id,v[(i-1)*3+1].id,v[(i-1)*3+2].id);
}
}
}
1004:Distinct Values
思路:优先队列暴力放入,模拟,不过好像会T,但是用set就不会T。。。
代码:
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e5+10;
pair<int,int>p[maxn];
int ans[maxn];
set<int>s;
bool cmp(pair<int,int> a,pair<int,int>b)
{
return a.first==b.first?a.second>b.second:a.first<b.first;
}
int main()
{
int t;scanf("%d",&t);
while(t--)
{
int n,m;scanf("%d%d",&n,&m);
for(int i=0;i<m;i++){
int l,r;scanf("%d%d",&l,&r);
p[i]=make_pair(l,r);
}
sort(p,p+m,cmp);s.clear();memset(ans,0,sizeof ans);
for(int i=1;i<=n;i++)s.insert(i);
int k=0,fi=1,prel=0,prer=0;
while(k<m){
int l=p[k].first,r=p[k].second;k++;
if(prel!=0 && prer!=0){
if(prer>=l && r>prer){
for(int i=prel;i<l;i++)s.insert(ans[i]);
}
else if(l>prer){
for(int i=prel;i<=prer;i++)s.insert(ans[i]);
}
}
if(ans[l]!=0 && ans[r]!=0)continue;
prel=l,prer=r;
if(ans[l]==0 && ans[r]==0){
while(fi<l){ans[fi]=1;fi++;}
while(fi<=r){ans[fi]=*s.begin();s.erase(s.begin());fi++;}
}
else if(ans[l]!=0 && ans[r]==0){
while(fi<=r){ans[fi]=*s.begin();s.erase(s.begin());fi++;}
}
}
while(fi<=n){ans[fi]=1;fi++;}
for(int i=1;i<n;i++)printf("%d ",ans[i]);
printf("%d\n",ans[n]);
}
}
1005:Maximum Weighted Matching
不会
1006:Period Sequence
不会
1007:Chiaki Sequence Revisited
思路:先打表,然后找规律。我找的规律是:设n是需要求的值,是小于n的最大值,那么
,在计算
时,
还需要减一。所以我是先暴力找出2的n次幂的值,一共62个,然后用
的算法去递归求出答案。
代码:
#include<bits/stdc++.h>
using namespace std;
const long long mod=1e9+7;
long long a[100];long long id[100];
long long solve(long long x)
{
long long ans=0;
int k=-1;
for(int i=0;i<=62;i++){
if(id[i]<=x)k=i;
}
if(id[k]==x)return a[k];
ans=a[k];
long long tk=id[k-1],f=x-tk*2;
long long ad=(tk%mod)*(f%mod);
ans=(ans+ad)%mod;ans-=1;
ans=ans+solve(f+1);
ans%=mod;
//cout<<ans<<endl;
return ans;
}
int main()
{
id[0]=1;for(int i=1;i<=62;i++)id[i]=id[i-1]*2;
a[0]=1;a[1]=2;a[2]=6;
for(int i=3;i<=62;i++){
long long aa=id[i-2]%mod;
aa=aa*((aa*2+1)%mod)%mod;
a[i]=(a[i-1]+a[i-1])%mod;
a[i]=(a[i]+aa-1)%mod;
//if(a[i]<0)cout<<i<<endl;
}
int t;scanf("%d",&t);
while(t--){
long long c;scanf("%lld",&c);
printf("%lld\n",solve(c));
}
}
1008:RMQ Similar Sequence
思路:构造出a数组的笛卡尔树,然后就可以求得b数组的笛卡尔树与a同构的概率是,也就是1除以每个位置的子树的大小。由于每个数是0到1随机的,所以期望是
,那么总期望就是
,所以答案就是
。其中,笛卡尔树的学习推荐一个链接:https://www.zybuluo.com/KirinBill/note/871204。
代码:
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int mod=1e9+7;
const int inf=0x3f3f3f3f;
const int mx=1e6+5;
struct node{
int val,sz;
int l,r,pre;
}t[mx];
stack<int>st;
void init(int n)
{
for(int i=0;i<=n;i++)t[i].l=t[i].r=t[i].pre=t[i].sz=0;
t[0].val=inf;
while(!st.empty())st.pop();
st.push(0);
}
void build(int n)
{
for(int i=1;i<=n;i++){
while(!st.empty() && t[st.top()].val<t[i].val)st.pop();
int pre=st.top();
t[i].pre=pre;t[i].l=t[pre].r;t[t[pre].r].pre=i;t[pre].r=i;
st.push(i);
}
}
void dfs(int u)
{
if(u==0)return ;
t[u].sz=1;
dfs(t[u].l);
dfs(t[u].r);
t[u].sz+=t[t[u].l].sz+t[t[u].r].sz;
}
ll inv[mx];
void init()
{
inv[1]=1;
for(int i=2;i<mx;i++)inv[i]=inv[mod%i]*(mod-mod/i)%mod;
}
int main()
{
int T;scanf("%d",&T);init();
while(T--){
int n;scanf("%d",&n);init(n);
for(int i=1;i<=n;i++)scanf("%d",&t[i].val);
build(n);dfs(t[0].r);
ll ans=n*inv[2]%mod;
for(int i=1;i<=n;i++)ans=ans*inv[t[i].sz]%mod;
printf("%lld\n",ans);
}
}
1009:Lyndon Substring
不会
1010:Turn Off The Light
不会
1011:Time Zone
思路:模拟。好像浮点数会有误差,所以不要用。
代码:
#include<cstdio>
#include<cstring>
using namespace std;
int flag,h,m,is;
char s[20];
void get()
{
if(s[3]=='+')flag=1;else flag=0;
int len=strlen(s);int i;
for(i=4;i<len;i++){
if(s[i]=='.')break;
else h=h*10+s[i]-'0';
}
if(i<len && s[i]=='.'){
is=1;m=s[i+1]-'0';
}
}
void print(int k)
{
int st=60*24;
if(k>=st)k-=st;
else if(k<0)k+=st;
if(k/60>=10)printf("%d",k/60);
else printf("0%d",k/60);
printf(":");
if(k%60>=10)printf("%d\n",k%60);
else printf("0%d\n",k%60);
}
int main()
{
int t;scanf("%d",&t);
while(t--){
int a,b;scanf("%d%d",&a,&b);
scanf("%s",&s);
flag=-1,h=0,m=0,is=0;get();
int x=a*60+b;
if(flag==1){
if(h>=8){
int tmp=(h-8)*60+m*6;
print(tmp+x);
}
else {
int tmp=(8-h)*60-m*6;
print(x-tmp);
}
}
else{
int tmp=8*60+h*60+m*6;
print(x-tmp);
}
}
}