题目大意:一个1~n的升序数字序列,有4种操作。操作1,将x放到y前面一个位置;操作2将x放到y后面的一个位置;操作3交换x和y的位置;操作4反转整个序列。求经过m次操作后的所有奇数项的和。

题目分析:建立双向链表,每次操作只需修改链表中的元素指向。

代码如下:

# include<iostream>
# include<cstdio>
# include<cstring>
# include<algorithm>
using namespace std; int l[100005],r[100005]; void link(int a,int b)
{
r[a]=b,l[b]=a;
} int main()
{
int n,m,op,x,y,flag,cas=0;
while(scanf("%d%d",&n,&m)==2)
{
for(int i=1;i<=n;++i)
r[i]=(i+1)%(n+1),l[i]=i-1;
r[0]=1,l[0]=n; flag=0;
while(m--)
{
scanf("%d",&op);
if(op==4)
flag=!flag;
else{
scanf("%d%d",&x,&y);
if(op==3&&r[y]==x)///方便下面的操作;
swap(x,y);
if(op!=3&&flag)
op=3-op;
if(op==1&&l[y]==x)
continue;
if(op==2&&r[y]==x)
continue; int lx=l[x],rx=r[x],ly=l[y],ry=r[y];
if(op==1){
link(lx,rx);
link(ly,x);
link(x,y);
}else if(op==2){
link(lx,rx);
link(y,x);
link(x,ry);
}else{
if(r[x]==y)
link(lx,y),link(y,x),link(x,ry);
else
link(lx,y),link(y,rx),link(ly,x),link(x,ry);
}
}
}
int k=0;
long long ans=0;
for(int i=1;i<=n;++i){
k=r[k];
if(i&1)
ans+=k;
}
if(flag&&n%2==0)
ans=(long long)n/2*(n+1)-ans;
printf("Case %d: %lld\n",++cas,ans);
}
return 0;
}

  

最新文章

  1. 简单总结java 语法
  2. PHPCMS 标签与示例
  3. srum.3
  4. 64 位 Ubuntu 下 android adb 不可用解决方法
  5. ViewPager中使用PhotoView时出现pointerIndex out of range异常
  6. HDOJ/HDU 1075 What Are You Talking About(字符串查找翻译~Map)
  7. AES - Rijndael 算法(一)
  8. djangoPOST请求403 forbidden
  9. js取整数、取余数的方法
  10. ecshop简单结构
  11. css background-position (图片裁取)
  12. android windows 上JNI编程
  13. c# 获取命名空间 类名 方法名
  14. salesforce零基础学习(七十八)线性表链形结构简单实现
  15. ssh、scp免秘钥远程执行命令:expect
  16. python写一个翻译的小脚本
  17. 安卓开发常用icon/png图样
  18. YOLOv3训练自己的数据
  19. react单组件 渲染页面
  20. .Net开源网络爬虫Abot介绍(转)

热门文章

  1. Oracle数据类型number
  2. Windows中的DNS服务——正向解析&amp;反向解析配置 分类: AD域 Windows服务 2015-07-16 20:21 19人阅读 评论(0) 收藏
  3. python操作mysql数据库读取一个数据库的表写入另一个数据库
  4. iptables 执行清除命令 iptables -F 要非常小心的
  5. python模块之xlrd(excl调用模块)
  6. 数据库知识,mysql索引原理
  7. POJ2891:Strange Way to Express Integers(解一元线性同余方程组)
  8. CSU 1642 Problem B[难][前缀和]
  9. JavaScript在页面中的引用方法
  10. 《FontForge常见问题FAQ》字王翻译版