先安利一下这套比赛,大概是doreamon搞的,每周五晚上有一场,虽然没人做题目质量挺高的 http://codeforces.com/group/gRkn7bDfsN/contests(报名前要先报名group,不用审核) 每一次的题解可以在这里看到 http://dreamoon4.blogspot.tw/(梯子自备)

这场是http://codeforces.com/group/gRkn7bDfsN/contest/210418

这一场是类似之前某一场cf把每题拆成几个数据规模的题目分别给分。之前连续出了两三场乱七八糟的构造题

A Apple Pen

给出n个字符串和一个母串,问这个母串能用多少种方式从n个字符串中选2个拼成并输出方案(可以假装方案不是很多)。2<=n<=10^6,字符串总长<=2e7,母串长度<=1e6。

喜闻乐见的样例。

这个题十分菜啊,假装每个字符串分别为前缀或者后缀判断是否可行,然后合在一起输出。之前脑子里进水了想了一堆奥妙重重的做法

#include <iostream>
#include <stdio.h>
#include <math.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>
#include <string>
#include <bitset>
#include <vector>
#include <set>
#include <map>
#include <queue>
#include <algorithm>
#include <sstream>
#include <stack>
#include <iomanip>
using namespace std;
#define pb push_back
#define mp make_pair
typedef pair<int,int> pii;
typedef long long ll;
typedef double ld;
typedef vector<int> vi;
#define fi first
#define se second
#define fe first
#define FO(x) {freopen(#x".in","r",stdin);freopen(#x".out","w",stdout);}
#define Edg int M=0,fst[SZ],vb[SZ],nxt[SZ];void ad_de(int a,int b){++M;nxt[M]=fst[a];fst[a]=M;vb[M]=b;}void adde(int a,int b){ad_de(a,b);ad_de(b,a);}
#define Edgc int M=0,fst[SZ],vb[SZ],nxt[SZ],vc[SZ];void ad_de(int a,int b,int c){++M;nxt[M]=fst[a];fst[a]=M;vb[M]=b;vc[M]=c;}void adde(int a,int b,int c){ad_de(a,b,c);ad_de(b,a,c);}
#define es(x,e) (int e=fst[x];e;e=nxt[e])
#define esb(x,e,b) (int e=fst[x],b=vb[e];e;e=nxt[e],b=vb[e])
#define VIZ {printf("digraph G{\n"); for(int i=1;i<=n;i++) for es(i,e) printf("%d->%d;\n",i,vb[e]); puts("}");}
#define VIZ2 {printf("graph G{\n"); for(int i=1;i<=n;i++) for es(i,e) if(vb[e]>=i)printf("%d--%d;\n",i,vb[e]); puts("}");}
#define SZ 1234567
int n;
string s[1000007];
string t;
char tmp[20000007];
vector<int> vs[1234567],vs2[1234567];
vector<pii> rst;
int main()
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%s",tmp); s[i]=tmp;
}
scanf("%s",tmp); t=tmp;
for(int i=1;i<=n;i++)
{
if(s[i].length()>t.length()) continue;
if(t.substr(0,s[i].length())==s[i])
vs[s[i].length()].pb(i);
if(t.substr(t.length()-s[i].length(),s[i].length())==s[i])
vs2[t.length()-s[i].length()].pb(i);
}
for(int i=0;i<t.length();i++)
{
for(auto a:vs[i])
{
for(auto b:vs2[i])
{
if(a==b) continue;
rst.pb(pii(min(a,b),max(a,b)));
}
}
}
sort(rst.begin(),rst.end());
rst.erase(unique(rst.begin(),rst.end()),rst.end());
printf("%d\n",rst.size());
for(int i=0;i<rst.size();i++) printf("%d %d\n",rst[i].fi,rst[i].se);
}

B Two Swords

有n把剑,有20种属性,每把可能会有或无每种属性,询问q次,每次要求找出两把剑,每种要求的属性至少要有一把剑具有,问找出这两把剑的方案数。n,q<=50W。

大概是个fwt/集合幂级数的裸题。

首先我们先把每种属性是否具有当做一个二进制数,拿个数组存下来每个二进制数出现的次数,就叫数组x好了。

那我们第一步就是要求

for(int i=0;i<(1<<20);i++)
for(int j=0;j<(1<<20);j++)
a[i|j]+=x[i]*x[j];

从fwt的角度理解:这就是个or的fwt,直接用fwt水~ http://picks.logdown.com/posts/179290-fast-walsh-hadamard-transform(我当时比赛时就是这么想的...)

从集合幂级数的角度理解:这就是个集合并卷积,我们可以用经典的快速莫比乌斯变换+快速莫比乌斯反演来做。(似乎ysy和出题人都是这么想的)

其实这两个做法只是同一个东西的两种写法...

这个数组求出来之后我们可以求出或恰好为一个数的方案数,但是题目中询问对不要求的属性不作要求,然后我们可以把每一位反过来,再用一发快速莫比乌斯变换。

#include <iostream>
#include <stdio.h>
#include <math.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>
#include <string>
#include <bitset>
#include <vector>
#include <set>
#include <map>
#include <queue>
#include <algorithm>
#include <sstream>
#include <stack>
#include <iomanip>
using namespace std;
#define pb push_back
#define mp make_pair
typedef pair<int,int> pii;
typedef long long ll;
typedef double ld;
typedef vector<int> vi;
#define fi first
#define se second
#define fe first
#define FO(x) {freopen(#x".in","r",stdin);freopen(#x".out","w",stdout);}
#define Edg int M=0,fst[SZ],vb[SZ],nxt[SZ];void ad_de(int a,int b){++M;nxt[M]=fst[a];fst[a]=M;vb[M]=b;}void adde(int a,int b){ad_de(a,b);ad_de(b,a);}
#define Edgc int M=0,fst[SZ],vb[SZ],nxt[SZ],vc[SZ];void ad_de(int a,int b,int c){++M;nxt[M]=fst[a];fst[a]=M;vb[M]=b;vc[M]=c;}void adde(int a,int b,int c){ad_de(a,b,c);ad_de(b,a,c);}
#define es(x,e) (int e=fst[x];e;e=nxt[e])
#define esb(x,e,b) (int e=fst[x],b=vb[e];e;e=nxt[e],b=vb[e])
#define VIZ {printf("digraph G{\n"); for(int i=1;i<=n;i++) for es(i,e) printf("%d->%d;\n",i,vb[e]); puts("}");}
#define VIZ2 {printf("graph G{\n"); for(int i=1;i<=n;i++) for es(i,e) if(vb[e]>=i)printf("%d--%d;\n",i,vb[e]); puts("}");}
#define SZ 666666
int mx=(1<<20);
int n,q;
ll cnt[2333333],qwq[2333333],inv[2333333];
char s[233];
int toi(char* s)
{
int x=0;
for(int i=0;s[i];i++) x=x*2+s[i]-48;
return x;
}
void trans(ll* g,int k)
{
for(int i=0;i<20;i++)
{
int all=(mx-1)^(1<<i);
for(int s=0;s<mx;s++)
{
if((s&all)!=s) continue;
g[s^(1<<i)]+=g[s]*k;
}
}
}
int main()
{
scanf("%d%d",&n,&q);
for(int i=1;i<=n;i++)
{
scanf("%s",s);
++cnt[toi(s)];
}
for(int i=0;i<mx;i++) qwq[i]=cnt[i];
trans(cnt,1);
for(int i=0;i<mx;i++) cnt[i]*=cnt[i];
trans(cnt,-1);
for(int i=0;i<mx;i++) inv[(mx-1)^i]=(cnt[i]-qwq[i])/2;
trans(inv,1);
while(q--)
{
scanf("%s",s);
int x=toi(s);
printf("%I64d\n",inv[(mx-1)^x]);
}
}

代码十分简洁明了。当然你可以把trans换成分治fwt效果是一样的= =

C Zekken

有一条数轴,你开始在0的位置,每单位时间你至多能移动d个单位,在ti时刻xi位置会出现一个宝物,然后马上消失,只有ti时刻你站在xi位置才能捡到。问最多你能捡到几个宝物。宝物数量n<=50W,没有ti、xi都相等的宝物。

先说结论,把一个点换成(ti*d-xi,ti*d+xi),如果有任一维<0就忽略这个点,否则将一维排序另一维lis即为答案。

我们先考虑d=1的情况,对于d≠1的显然只要把一秒续成d秒就行了(即ti*=d)。

我们考虑把(xi,ti)当做一个点,显然下一个点只能在左右45°内

我们往右转45°就变成了要在这个点的右上方,(a,b)右转45°就成了((a+b)/sqrt(2),(b-a)/sqrt(2)),我们忽略那个sqrt(2),(xi,ti)转完就相当于(xi+ti,ti-xi)。

#include <iostream>
#include <stdio.h>
#include <math.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>
#include <string>
#include <bitset>
#include <vector>
#include <set>
#include <map>
#include <queue>
#include <algorithm>
#include <sstream>
#include <stack>
#include <iomanip>
using namespace std;
#define pb push_back
#define mp make_pair
typedef pair<int,int> pii;
typedef long long ll;
typedef double ld;
typedef vector<int> vi;
#define fi first
#define se second
#define fe first
#define FO(x) {freopen(#x".in","r",stdin);freopen(#x".out","w",stdout);}
#define Edg int M=0,fst[SZ],vb[SZ],nxt[SZ];void ad_de(int a,int b){++M;nxt[M]=fst[a];fst[a]=M;vb[M]=b;}void adde(int a,int b){ad_de(a,b);ad_de(b,a);}
#define Edgc int M=0,fst[SZ],vb[SZ],nxt[SZ],vc[SZ];void ad_de(int a,int b,int c){++M;nxt[M]=fst[a];fst[a]=M;vb[M]=b;vc[M]=c;}void adde(int a,int b,int c){ad_de(a,b,c);ad_de(b,a,c);}
#define es(x,e) (int e=fst[x];e;e=nxt[e])
#define esb(x,e,b) (int e=fst[x],b=vb[e];e;e=nxt[e],b=vb[e])
#define VIZ {printf("digraph G{\n"); for(int i=1;i<=n;i++) for es(i,e) printf("%d->%d;\n",i,vb[e]); puts("}");}
#define VIZ2 {printf("graph G{\n"); for(int i=1;i<=n;i++) for es(i,e) if(vb[e]>=i)printf("%d--%d;\n",i,vb[e]); puts("}");}
#define SZ 666666
typedef pair<ll,ll> pll;
int n,d,x[SZ],t[SZ],bs[SZ],dp[SZ];
ll gg[SZ],tmp[SZ];
pll ps[SZ];
int mx(int g)
{
int ans=0;
for(;g>=1;g-=g&-g) ans=max(ans,bs[g]);
return ans;
}
void edt(int x,int y)
{
for(;x<=n;x+=x&-x) bs[x]=max(bs[x],y);
}
int main()
{
scanf("%d%d",&n,&d);
for(int i=1;i<=n;i++)
{
scanf("%d%d",x+i,t+i);
ps[i]=pll(t[i]*(ll)d-x[i],t[i]*(ll)d+x[i]);
if(ps[i].fi<0||ps[i].se<0)
{
--i; --n; continue;
}
}
sort(ps+1,ps+1+n);
for(int i=1;i<=n;i++) gg[i]=ps[i].se;
for(int i=1;i<=n;i++) tmp[i]=gg[i];
sort(tmp+1,tmp+1+n);
int ans=0;
for(int i=1;i<=n;i++)
{
gg[i]=(lower_bound(tmp+1,tmp+1+n,gg[i])-tmp);
dp[i]=mx(gg[i])+1; edt(gg[i],dp[i]);
ans=max(ans,dp[i]);
}
printf("%d\n",ans);
}

Weekly Traning Farm 16的更多相关文章

  1. SharePoint 解决方案和功能-PowerShell

    1. 添加解决方案到SharePoint场 Add-SPSolution "c:\newsolution.wsp" 2. 获取场中的解决方案 Get-SPSolution 3. 获 ...

  2. CI Weekly #16 | 从另一个角度看开发效率:flow.ci 数据统计功能上线

    很开心的告诉大家,flow.ci 数据统计功能已正式上线. 进入 flow.ci 控制台,点击「数据分析」按钮,你可以按照时间日期筛选,flow.ci 将多维度地展示「组织与项目」的构建数据指标与模型 ...

  3. Murano Weekly Meeting 2016.08.16

    Meeting time: 2016.August.16 1:00~2:00 Chairperson:  Kirill Zaitsev, from Mirantis Meeting summary: ...

  4. CI Weekly #6 | 再谈 Docker / CI / CD 实践经验

    CI Weekly 围绕『 软件工程效率提升』 进行一系列技术内容分享,包括国内外持续集成.持续交付,持续部署.自动化测试. DevOps 等实践教程.工具与资源,以及一些工程师文化相关的程序员 Ti ...

  5. fir.im Weekly - 揭秘 iOS 面向协议编程

    本期 fir.im Weekly 重点推荐关于 iOS 面向协议编程相关文章,还有 iOS 多线程安全.Swift 进阶.Android MVVM 应用框架.Android 蓝牙实践等技术文章分享和工 ...

  6. How To Collect ULS Log from SharePoint Farm

    We can use below command to collect SharePoint ULS log from all servers in the Farm in PowerShell. M ...

  7. fir.im Weekly - 这是一份强大的 SwiftGuide

    大新闻!Apple 10 亿美元融资滴滴!库克大叔对中国 iOS 开发者表达了高度认可,同时也传出 iOS 10 将内置滴滴 App 的消息.想像下,某个加班的深夜飙完代码,最性感的事情莫过于:「Si ...

  8. fir.im Weekly - Stanford 的 Swift 课程来了

    上周提过,Swift 的 Github 主页上已经有了 >>「Port to Android」,这周重点推荐一下 Stanford 的 Swift 课程. Developing iOS 9 ...

  9. fir.im Weekly - 论个人技术影响力是如何炼成的

    每个圈子都有一群能力强且懂得经营自己的人,技术圈也是如此.本期 fir.im Weekly 一如往期精选了一些实用的 iOS,Android 开发工具和源码分享,还有一些关于程序员的成长 Tips 和 ...

随机推荐

  1. JS处理事件小技巧

    今天,就分享一下我自己总结的一些JS的小技巧: ①防止鼠标选中事件 <div class="mask" onselectstart="return false&qu ...

  2. ASP.NET Core 中文文档 第三章 原理(12)托管

    原文:Hosting 作者:Steve Smith 翻译:娄宇(Lyrics) 校对:何镇汐.许登洋(Seay) 为了运行 ASP.NET Core 应用程序,你需要使用 WebHostBuilder ...

  3. ASP.NET Core 中文文档 第四章 MVC(3.1)视图概述

    原文:Views Overview 作者:Steve Smith 翻译:姚阿勇(Dr.Yao) 校对:高嵩(Jack) ASP.NET MVC Core 的控制器可以利用 视图 返回格式化结果. 什么 ...

  4. java设计模式之简单工厂模式

    简单工厂: 简单工厂的优点: 1.去除客户端与具体产品的耦合,在客户端与具体的产品中增加一个工厂类,增加客户端与工厂类的耦合 2.封装工厂类,实现代码平台的复用性,创建对象的过程被封装成工厂类,可以多 ...

  5. 数据库进阶之路(五) - MySQL行锁深入研究

    由于业务逻辑的需要,必须对数据表的一行或多行加入行锁,举个最简单的例子,图书借阅系统:假设id=1的这本书库存为1,但是有2个人同时来借这本书,此处的逻辑为: ; --如果restnum大于0,执行u ...

  6. .NET Core之Entity Framework Core 你如何创建 DbContext

    本文版权归博客园和作者吴双共同所有,欢迎转载,转载和爬虫请注明博客园蜗牛原文地址 http://www.cnblogs.com/tdws/p/5874212.html. 目前国内各大论坛,各位大牛的分 ...

  7. java异常处理(父子异常的处理)

    我当初学java异常处理的时候,对于父子异常的处理,我记得几句话“子类方法只能抛出父类方法所抛出的异常或者是其子异常,子类构造器必须要抛出父类构造器的异常或者其父异常”.那个时候还不知道子类方法为什么 ...

  8. 在xcode中用 swift 进行网络服务请求

    xcode集成开发环境是运行于Mac苹果电脑上用于开发swift应用程序的工具,利用xcode可以很方便.直观的开发OS X和iOS系统所支持的应用程序. 1 开发环境: Mac OS 10.11 X ...

  9. ES6之解构赋值

    截止到ES6,共有6种声明变量的方法,分别是var .function以及新增的let.const.import和class: 我们通常的赋值方法是: var foo='foo'; function ...

  10. sass安装

    第一步:下载ruby http://www.ruby-lang.org/zh_cn/downloads/ 第二步:安装ruby http://www.ruby-lang.org/zh_cn/docum ...