时间限制 5000 ms 内存限制 65536 KB

题目描述

One day, the teacher asked Weishen to judge whether a binary string can be divided by 3 (3=(11)2) in binary system. 
    "It’s too simple.", Weishen said, and solved it quickly. 
    Teacher was very angry, he decided to teach Weishen some life experience.
    So he added '?' characters to the 01 string, '?' can replace either 0 or 1 respectively.  
    This time he askes Weishen to calculate the expected number of substrings that can be divided by 3 if each '?' randomly replaces '0' or '1'. Note that the substrings can not contain leading zeroes, thus you should ignore substrings like (011)2. Weishen would like you to help him solve this problem.

输入格式

The input begins with a line containing a single integer T(1≤T≤50  ), indicating the number of test cases. For each test case, the first line contains one integers N(1≤N≤100000), indicating the length of the string. The next lines is the string containing Ncharacters given by the teacher. It is guaranteed that only characters '0', '1', and '?' would appear in the strings.

输出格式

For each case, please output a line containing a real number rounded to the second decimal place, indicating the answer.

Explanation of example

For the first case '01?', if this '?' represent '0', then we get '010', there are two substrings divisible by 3: '0' and '0'. If this '?' represent '1', we get '011' and there are also two substrings divizible by 3: '0' and '11'. String '011'has leading zeroes and we have to omit it. The expected number of substrings will be (2+2)/2=2.

输入样例

1
3
01?

输出样例

2.00

题意是给你一个长度最大10^5的二进制01串,其中有些位置被?模糊了,问所有的可能性里,所有的能被3整除的子串的数量的期望值是多少,期望DP。

样例解释:01?

0.5概率?是1, 011里,0和11都可以被3整除

0.5概率?是0, 010里,第一个0和第三个0都可以被3整除

所以0.5*2+0.5*2=2

因为要求被3整除,所以设dp[100000+5][3],dp[i][j]表示以i位结尾的模3余数为j的子串的数量有多少。

然后有12种状态转移,null代表开头第一位前面没有字符,其余的都代表由前一位转移到当前位的字符变化情况

null->0,null->1,null->?

0->0,0->1,0->?

1->0,1->1,1->?

?->0,?->1,?->?

我们知道,对元二进制串A后加一位0意味着A*2,根据模运算

①A%3==1,(A*2)%3==2

②A%3==2,(A*2)%3==1

③A%3==0,(A*2)%3==0
所以状态转移方程里,转移到当前位是0的情况里,一定都都要有dp[i][1]=dp[i-1][2],  dp[i][2]=dp[i-1][1]

我们又知道,对元二进制串A后加一位1意味着A*2+1,根据模运算

①A%3==1,(A*2+1)%3==0

②A%3==2,(A*2+1)%3==2

③A%3==0,(A*2+1)%3==1

转移到当前位是1的情况里,一定都要有dp[i][2]=dp[i-1][2], dp[i][0]=dp[i-1][1]

然后我们具体来看各个转移

1.我们来看0->0的情况显然,以前一个0结尾的可以被3整除的数,*2还是可以被整除,所以dp不变,比如110,1100,以第三位结尾的有110、0,以第4位结尾的,1100、0,没有任何变化。dp[i][0]=dp[i-1][0]

2.再来看1->0的情况,显然以前一个1结尾的可以被3整除的数,*2还是可以被整除,但新增加了一个单个的0,所以dp+1,dp[i][0]=dp[i-1][0]+1

3.如果是?->0的话,显然0->0和1->0各占50%,dp+0.5,dp[i][0]=dp[i-1][0]+0.5

4.如果是null->0的话,显然+1,因为增加了单个0.

我们再来看->1的情况,因为前一位%3==1和%3==2的情况的情况都讲明了,所以在此只看%3==0的部分

5.我们来看0->1的情况,*2+1,举个例子,100->1001, dp[3][0]=1, dp[4][1]=1, dp[i][1]=dp[i-1][0]

6.1->1的情况,举个例子,101->1011,dp[3][0]=0, dp[4][1]=1, dp[i][1]=dp[i-1][0]+1, 为什么都是*2+1,它却要额外dp+1呢,因为1变成11, 11可以被3整除,所以要+1

7.如果是?->1的话,显然dp+0.5,dp[i][0]=dp[i-1][0]+0.5

然后字符->?后续的情况把上面都加概率仔细算一下就好

代码略长

#include<cstdio>
#include<cmath>
#include<algorithm>
#define N 100050
using namespace std;
char str[N];
double dp[N][3];
int main(){int t,n,i;for(scanf("%d",&t);t--;){scanf("%d",&n);scanf("%s",str+1);dp[0][0]=dp[0][1]=dp[0][2]=0;str[0]='Z';double res=0;for(i=1;i<=n;i++){if(str[i]=='0'){if(str[i-1]=='0'){dp[i][0]=dp[i-1][0];}else if(str[i-1]=='1'){dp[i][0]=dp[i-1][0]+1;}else if(str[i-1]=='?'){dp[i][0]=dp[i-1][0]+0.5;}else {dp[i][0]=dp[i-1][0]+1;}dp[i][1]=dp[i-1][2];dp[i][2]=dp[i-1][1];}else if(str[i]=='1'){if(str[i-1]=='0'){dp[i][1]=dp[i-1][0];}else if(str[i-1]=='1'){dp[i][1]=dp[i-1][0]+1;//*2+1,1mod 3==1}else if(str[i-1]=='?'){dp[i][1]=dp[i-1][0]+0.5;}else{dp[i][1]=dp[i-1][0]+1;}dp[i][2]=dp[i-1][2];dp[i][0]=dp[i-1][1];//no add 0}else {dp[i][0]=0.5*dp[i-1][1];dp[i][1]=0.5*dp[i-1][2];dp[i][2]=0.5*dp[i-1][1]+0.5*dp[i-1][2];if(str[i-1]=='0'){dp[i][0]+=dp[i-1][0]*0.5;dp[i][1]+=dp[i-1][0]*0.5;}else if(str[i-1]=='1'){dp[i][0]+=(dp[i-1][0]+1)*0.5;dp[i][1]+=(dp[i-1][0]+1)*0.5;}else if(str[i-1]=='?'){dp[i][0]+=(dp[i-1][0]+0.5)*0.5;dp[i][1]+=(dp[i-1][0]+0.5)*0.5;}else{dp[i][0]+=(dp[i-1][0]+1)*0.5;dp[i][1]+=(dp[i-1][0]+1)*0.5;}}}for(i=1;i<=n;i++)res=res+dp[i][0];printf("%.2lf\n",res);}return 0;
}

北邮OJ 1010. 16校赛-Binary Strings相关推荐

  1. 北邮OJ 1005. 16校赛-Hawei Learning C

    时间限制 1000 ms 内存限制 65536 KB 题目描述 Hawei is learning C programming language recently, but he is so naiv ...

  2. 北邮OJ 981. 16校赛-Saber's Number Game

    时间限制 1000 ms 内存限制 65536 KB 题目描述 Saber is fond of number games of various kinds, she particularly lik ...

  3. 北邮OJ 1027. 16校赛-Archer in Archery

    时间限制 1000 ms 内存限制 65536 KB 题目描述 Archer(Emiya), also known as the red A, is famous for his talented s ...

  4. 北邮OJ 1022. 16校赛-Saber's Board

    时间限制 5000 ms 内存限制 65536 KB 题目描述 In a parallel universe, Saber has won the champion of every kind of ...

  5. 北邮OJ 1021. 16校赛-Stone Game

    时间限制 4000 ms 内存限制 65536 KB 题目描述 Alice and Bob are old friends in game theory. This afternoon they me ...

  6. 北邮OJ 980. 16校赛-R_clover's Challenge

    时间限制 2000 ms 内存限制 65536 KB 题目描述 R_clover wants to challenge Mengmengda_wsw's math,so he give her a f ...

  7. 北邮OJ 884. 16校赛-Average Modulo

    时间限制 5000 ms 内存限制 65536 KB 题目描述 We define function g on an array as: g([a0,a1,⋯,an−1])=(Σn−1l=0al) m ...

  8. 北邮oj题库刷题计划(更新ing)

    北邮oj题库刷题计划(更新ing) 83. A + B Problem 84 Single Number 85. Three Points On A Line 120 日期 121 最值问题 122 ...

  9. 北邮OJ 141 虚数

    北邮OJ 虚数 #include <bits/stdc++.h> using namespace std; typedef struct fushu{int x; //实部 int y; ...

最新文章

  1. 独家 | ​采用BERT的无监督NER(附代码)
  2. 如何用最短时间搞定酷炫可视化大屏?这款工具值得一看
  3. PHP命令注入 Command injection
  4. C++:52---多重继承
  5. Angular 单元测试讲解
  6. js 设置password placeholder样式_150+ 个优质的 Node.js 包和资源
  7. 华为网络配置(路由配置)
  8. 【Photoshop 教程系列第 3 篇】如何在 PS 中修改图片的分辨率和大小(一步一步详细说明)
  9. pyecharts动态图表嵌入ppt
  10. mysql next key_关于mysql next-key锁的一些个人理解
  11. git目录下object文件过大清理
  12. 充电口 米兔积木机器人_米兔积木机器人怎么充电
  13. 华为系统更新彻底卸载_华为手机系统更新好吗 华为手机系统更新方法
  14. (转)如何获得两个日期相减的天数?
  15. 文件上传中关于MultipartResolver的配置
  16. python编码声明问题
  17. fts touchscreen
  18. 迭代速度慢?成熟的机器学习流如何设计:微博大规模机器学习框架Weiflow揭秘...
  19. java 延时发送邮件_基于SpringBoot实现定时发送邮件过程解析
  20. 网页设计配色应用实例剖析——红色系

热门文章

  1. DNN盛行的当下,老旧的核(kernel)方法或能打开神经网络的魔盒
  2. TensorSpace:超酷炫3D神经网络可视化框架
  3. 高效CNN推理库、多款AlphaGo实现…你们喜欢的Github项目精选又来了!
  4. 【华为云踩坑】开启了入方向规则的 tcp/80 端口,仍然无法访问
  5. POJ 3984 迷宫问题 BFS求最短路线+路径记录
  6. yii2 java_YII2 自定义日志路径
  7. python读取word指定内容_python解析html提取数据,并生成word文档实例解析
  8. 【LeetCode】LeetCode之删除并获得点数——动态规划、排序+动态规划
  9. Spring Boot简介
  10. 《IBM-PC汇编语言程序设计》(第2版)【沈美明 温冬婵】——第十章——自编解析与答案