nenu contest3

时间:2022-01-10 08:26:12

http://vjudge.net/contest/view.action?cid=55702#overview

12656 - Almost Palindrome http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4394

先把原串处理成只有小写的,然后枚举每一个位置,可以以它为中心向两边扩展,回文可以是奇数,也可以是偶数,分类讨论,如果两边不一样,那么容量加一,容量小于k都行。

 #include<cstdio>
#include<cctype>
const int M=;
char a[M],b[M];
int p[M];
int main(){
int n,cas=;
while(~scanf("%d",&n)){
getchar();
gets(a);
int lb=;
for(int i=;a[i];i++){
if(isalpha(a[i])){
p[lb]=i;
b[lb++]=tolower(a[i]);
}
}
int big=,id;
for(int i=;i<lb;i++){
int cnt=;
for(int j=;i-j>=&&i+j<lb;j++){///奇数
if(b[i-j]!=b[i+j]) cnt++;
if(cnt>n) break;
int prelen=p[i+j]-p[i-j]+;
if(big<prelen){
big=prelen;
id=p[i-j];
}
}
cnt=;
for(int j=;i-j>=&&i+j+<lb;j++){///偶数
if(b[i-j]!=b[i+j+]) cnt++;
if(cnt>n) break;
int prelen=p[i+j+]-p[i-j]+;
if(big<prelen){
big=prelen;
id=p[i-j];
}
}
}
printf("Case %d: %d %d\n",cas++,big,id+);
}
return ;
}

12658 - Character Recognition?  http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4396

123识别,找不同。

 #include<cstdio>
char a[][];
int main(){
int n;
while(~scanf("%d",&n)){
for(int i=;i<;i++){
scanf("%s",a[i]);
}
for(int i=,y=;i<n;i++,y+=){
if(a[][y]=='.'){
printf("");
continue;
}
if(a[][y+]=='.'){
printf("");
continue;
}
printf("");
}
puts("");
}
return ;
}

12661 - Funny Car Racing http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4399

bfs,记忆化搜索dp,注意t>a的边就别加了

 #include<cstdio>
#include<cstring>
#include<queue>
#define mt(a,b) memset(a,b,sizeof(a))
using namespace std;
typedef long long LL;
const LL inf=0x3f3f3f3f3f3f3f3fLL;
const int M=;
struct G{
struct E{
int v,next,a,b,t;
}e[];
int le,head[M];
void init(){
le=;
mt(head,-);
}
void add(int u,int v,int a,int b,int t){
e[le].v=v;
e[le].a=a;
e[le].b=b;
e[le].t=t;
e[le].next=head[u];
head[u]=le++;
}
}g;
LL dp[M];
queue<int> q;
void bfs(int s){
for(int i=;i<M;i++){
dp[i]=inf;
}
dp[s]=;
while(!q.empty()) q.pop();
q.push(s);
while(!q.empty()){
int u=q.front();
q.pop();
LL pretime=dp[u],cost;
for(int i=g.head[u];~i;i=g.e[i].next){
int v=g.e[i].v;
int a=g.e[i].a;
int b=g.e[i].b;
int t=g.e[i].t;
LL now=pretime%(a+b);
if(now+t<=a){
cost=t;
}
else{
cost=a+b-now+t;
}
cost+=pretime;
if(dp[v]>cost){
dp[v]=cost;
q.push(v);
}
}
}
}
int main(){
int n,m,s,t,cas=;
while(~scanf("%d%d%d%d",&n,&m,&s,&t)){
g.init();
while(m--){
int u,v,a,b,c;
scanf("%d%d%d%d%d",&u,&v,&a,&b,&c);
if(c>a) continue;
g.add(u,v,a,b,c);
}
bfs(s);
printf("Case %d: %lld\n",cas++,dp[t]);
}
return ;
}

12662 - Good Teacher http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4400

简单题 注意细节,最坏情况也就是n^2,预处理出最近的。

 #include<cstdio>
#include<cstring>
struct G{
char name[],left[],right[];
int L,R;
}g[];
int main(){
int n,m,q;
while(~scanf("%d",&n)){
for(int i=;i<=n;i++){
scanf("%s",g[i].name);
}
for(int i=;i<=n;i++){
if(g[i].name[]=='?'){
int id=i;
for(int j=i;j<=n;j++){
if(g[j].name[]!='?'){
id=j;
break;
}
}
g[i].R=id-i;
if(id==i) g[i].R=;
strcpy(g[i].right,g[id].name);
id=i;
for(int j=i;j>=;j--){
if(g[j].name[]!='?'){
id=j;
break;
}
}
g[i].L=i-id;
if(id==i) g[i].L=;
strcpy(g[i].left,g[id].name);
}
}
scanf("%d",&m);
while(m--){
scanf("%d",&q);
if(g[q].name[]!='?'){
puts(g[q].name);
continue;
}
if(g[q].L==g[q].R){
printf("middle of %s and %s\n",g[q].left,g[q].right);
continue;
}
if(g[q].L<g[q].R){
for(int i=;i<g[q].L;i++){
printf("right of ");
}
puts(g[q].left);
continue;
}
for(int i=;i<g[q].R;i++){
printf("left of ");
}
puts(g[q].right);
}
}
return ;
}

12663 - High bridge, low bridge http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4401

离线的区间累加和是可以左++右--on处理的,当然如果是线段树树状数组都会多个logn,不好 不好

 #include<cstdio>
#include<algorithm>
using namespace std;
const int M=;
int a[M],lazy[M];
int main(){
int n,m,k,cas=;
while(~scanf("%d%d%d",&n,&m,&k)){
for(int i=;i<n;i++){
scanf("%d",&a[i]);
lazy[i]=;
}
sort(a,a+n);
int prehigh=,nowa,nowb;
while(m--){
scanf("%d%d",&nowa,&nowb);
int s=upper_bound(a,a+n,prehigh)-a;
int e=upper_bound(a,a+n,nowa)-a;
lazy[s]++;
lazy[e]--;
prehigh=nowb;
}
int now=,ans=;
for(int i=;i<n;i++){
now+=lazy[i];
if(now>=k) ans++;
}
printf("Case %d: %d\n",cas++,ans);
}
return ;
}

12664 - Interesting Calculator http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4402

听说搜索剪枝能过,因为时限大吧,一开始想二维dp,但是不对,用dp i j 表示第 i 个数在第 j 步到达的最小花费,因为可能一步就加了1,所以第二维也可能达到10^5,完全干不动。   仔细考虑了一下,除了*0这种操作, 其余都会使得当前的数变大。所以当x不等于0时,dp 0 只要1步, 然后从小往大的更新最小费用, 因为除了这种情况 其他的值都是从比自己小的值推过来的。

 #include<cstdio>
#include<algorithm>
using namespace std;
typedef long long LL;
const LL inf=0x3f3f3f3f3f3f3f3fLL;
const int M=;
LL dp[M];
int step[M];
int val[][];
int main(){
int x,y,cas=;
while(~scanf("%d%d",&x,&y)){
for(int i=;i<;i++){
for(int j=;j<;j++){
scanf("%d",&val[i][j]);
}
}
for(int i=;i<=y;i++){
dp[i]=inf;
step[i]=0x3f3f3f3f;
}
dp[x]=;
step[x]=;
if(x){
dp[]=val[][];
step[]=;
}
for(int i=;i<y;i++){
for(int j=;j<;j++){
for(int k=;k<;k++){
int next;
if(j==){
next=i*+k;
}
else if(j==){
next=i+k;
}
else{
next=i*k;
}
if(next>y) continue;
LL cost=dp[i]+val[j][k];
if(dp[next]>cost){
dp[next]=cost;
step[next]=step[i]+;
}
else if(dp[next]==cost){
step[next]=min(step[next],step[i]+);
}
}
}
}
printf("Case %d: %lld %d\n",cas++,dp[y],step[y]);
}
return ;
}

12665 - Joking with Fermat's Last Theorem http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4403

a,b在1000就够了,所以可以暴力的去判断

 #include<cstdio>
int x,y,cas=;
bool ok(int a){
return a>=x&&a<=y;
}
int main(){
while(~scanf("%d%d",&x,&y)){
int ans=;
for(int i=;i<;i++){
for(int j=;j<;j++){
if(ok(i)&&ok(j)){
int left=i*i*i+j*j*j;
if(left%==){
int c=left/;
if(ok(c)){
ans++;
}
}
}
}
}
printf("Case %d: %d\n",cas++,ans);
}
return ;
}

12667 - Last Blood http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4405

唯一的坑就是如果一个队ac一个题,那要算最早ac的时间。

 #include<cstdio>
struct G{
int t,id;
}g[];
char p[],yes[];
bool mat[][];
int main(){
int n,t,m,x,y;
while(~scanf("%d%d%d",&n,&t,&m)){
for(int i=;i<n;i++){
g[i].t=-;
for(int j=;j<=t;j++){
mat[i][j]=false;
}
}
while(m--){
scanf("%d%d%s%s",&x,&y,p,yes);
if(yes[]=='N') continue;
int pp=p[]-'A';
if(mat[pp][y]) continue;
mat[pp][y]=true;
g[pp].t=x;
g[pp].id=y;
}
for(int i=;i<n;i++){
printf("%c ",i+'A');
if(g[i].t!=-){
printf("%d %d\n",g[i].t,g[i].id);
}
else{
puts("- -");
}
}
}
return ;
}

end

相关文章