贴nescafe 26 div2两道程序
描述 DescriptionFreda发明了传呼机之后,rainbow进一步改进了传呼机发送信息所使用的信号。由于现在是数字、信息时代,rainbow发明的信号用N个自然数表示。为了避免两个 人的对话被大坏蛋VariantF偷听T_T,rainbow把对话分成A、B、C三部分,分别用a、b、c三个密码加密。现在Freda接到了 rainbow的信息,她的首要工作就是解密。Freda了解到,这三部分的密码计算方式如下:
在1~N这N个数中,等概率地选取两个数l、r,如果l>r,则交换l、r。把信号中的第l个数到第r个数取出来,构成一个数列P。 A部分对话的密码是数列P的xor和的数学期望值。xor和就是数列P中各个数异或之后得到的数; xor和的期望就是对于所有可能选取的l、r,所得到的数列的xor和的平均数。 B部分对话的密码是数列P的and和的期望,定义类似于xor和。 C部分对话的密码是数列P的or和的期望,定义类似于xor和。 |
输入格式 InputFormat第一行一个正整数N。
第二行N个自然数,表示Freda接到的信号。 |
输出格式 OutputFormat一行三个实数,分别表示xor和、and和、or和的期望,四舍五入保留3位小数,相邻两个实数之间用一个空格隔开。
|
样例输入 SampleInput样例输入1 2 4 5 样例输入2 3 1 0 1 |
样例输出 SampleOutput样例输出1 2.750 4.250 4.750 样例输出2 0.667 0.222 0.889 |
数据范围和注释 Hint数据范围与约定
对于20%的数据,1<=N<=100。 对于40%的数据,1<=N<=1000。 对于另外30%的数据,N个数为0或1。 对于100%的数据,1<=N<=100000,N个自然数均不超过10^9。 样例解释 样例1共包含四种可能的l、r: l, r xor和 and和 or和 1,1 4 4 4 1,2 1 4 5 2,1 1 4 5 2,2 5 5 5 以上每一对l、r出现的概率均相同,因此分别对xor和、and和、or和取平均数就是数学期望值。 |
时间限制 TimeLimitation各个测试点1s
|
program P2021; Var f,pre0,pre1:array[0..31,0..100000] of longint; a:array[0..100000,0..31] of integer; n,i,j,x,oddt,oddf:longint; ct:qword; ans:extended; Procedure swap(var p,q:longint); var y:longint; begin y:=p; p:=q; q:=y; end; Procedure fopen; begin assign(input,'p2021.in'); assign(output,'p2021.out'); reset(input); rewrite(output); end; Procedure fclose; begin close(input); close(output); end; begin fopen; readln(n); for i:=1 to n do begin read(x); ct:=-1; while x<>0 do begin inc(ct); inc(a[i,ct],x mod 2); x:=x div 2; end; end; for i:=0 to 31 do for j:=2 to n do if a[j-1,i]=0 then pre0[i,j]:=j-1 else pre0[i,j]:=pre0[i,j-1]; for i:=0 to 31 do for j:=2 to n do if a[j-1,i]=1 then pre1[i,j]:=j-1 else pre1[i,j]:=pre1[i,j-1]; {for i:=0 to 17 do begin for j:=1 to n do write(pre0[i,j],' '); writeln; end; } readln; ans:=0; for i:=0 to 31 do begin ct:=0; //odd T oddt:=0; //odd F oddf:=0; if a[1,i]=1 then ct:=1; for j:=2 to n do begin if a[j-1,i]=1 then begin swap(oddt,oddf); inc(oddt); end else inc(oddf); if a[j,i]=1 then inc(ct,2*oddf+1) else inc(ct,2*oddt); end; ans:=ans+(ct/(qword(n)*qword(n)))*qword((1 shl i)); end; write(ans:0:3,' '); ans:=0; for i:=0 to 31 do begin ct:=0; for j:=1 to n do if a[j,i]=1 then ct:=ct+2*(j-1-pre0[i,j])+1; // writeln('I=',i,' J=',j,' pre=',pre0[i,j]); //writeln('I=',i,' AND CT=',ct); ans:=ans+ct/(qword(n)*qword(n))*qword((1 shl i)); end; write(ans:0:3,' '); ans:=0; for i:=0 to 31 do begin ct:=0; for j:=1 to n do if a[j,i]=1 then inc(ct,2*(j-1)+1) else inc(ct,2*pre1[i,j]); // writeln('I=',i,' OR CT=',ct); ans:=ans+ct/(qword(n)*qword(n))*qword((1 shl i)); end; writeln(ans:0:3); fclose; end.
P2022 - Freda的队列
描述 DescriptionFreda有一个队列,最初它是空的。
现在Freda接到了一系列指令,每个指令包含一个整数x。 如果x>0,表示在队列开头加入一个数x。 如果x=0,表示把队列复制一份,并接在现有队列的末尾。 如果x=-1,表示弹出队列头部的数,并输出这个数值。 但是指令实在是太多了,Freda实在是计算不过来每次要输出什么数值,请你帮帮她吧。 |
输入格式 InputFormat第一行包含一个整数N,表示指令的个数。
接下来N行每行一个整数x,描述每条指令。 |
输出格式 OutputFormat对于每条x=-1的指令,若此时队列不为空,则输出一个整数,表示从队头弹出的数。否则不进行任何操作。
|
样例输入 SampleInput8 3 4 0 -1 -1 -1 -1 1 |
样例输出 SampleOutput4 3 4 3 |
数据范围和注释 Hint对于50%的数据,1<=N<=1000.
对于100%的数据,1<=N<=10^6,-1<=x<=10^9。 |
时间限制 TimeLimitation各个测试点1s
|
program p2022; Var n,i,j,x,p,q:longint; a:array[-4000000..4000000] of longint; Procedure fopen; begin assign(input,'p2022.in'); assign(output,'p2022.out'); reset(input); rewrite(output); end; Procedure fclose; begin close(input); close(output); end; begin fopen; p:=1;q:=0; readln(n); for i:=1 to n do begin readln(x); if x>0 then begin dec(p); a[p]:=x; end; if x=0 then if (q-p<=1000000) and (q>=p) then begin for j:=1 to q-p+1 do a[q+j]:=a[p+j-1]; q:=q+q-p+1; end; if x<0 then if q>=p then begin writeln(a[p]); inc(p); end; end; fclose; end.