您的位置:首页 > 其它

排列统计 jzoj 1283

2016-10-06 17:23 211 查看
Description

  对于给定的一个长度为n的序列{B
},问有多少个序列{A
}对于所有的i满足:A[1]~A[i]这i个数字中有恰好B[i]个数字小等于i。其中{A
}为1~n的一个排列,即1~n这n个数字在序列A[I]中恰好出现一次。

  数据保证了至少有一个排列满足B序列。

Input

  输入的第1行为一个正整数N,表示了序列的长度。

  第2行包含N个非负整数,描述了序列{B[i]}。

Output

  输出仅包括一个非负整数,即满足的{A[i]}序列个数。

题解

b[i]-b[i-1]=1 时 ans=ans*2*i-1-2*b[i-1]

b[i]-b[i-1]=2 时 ans=ans*sqr((i-1-b[i-1]))

要用高精度

代码

const
mo=100000000;
var
n:longint;
b:array[0..2001] of longint;
a:array [0..1001] of int64;
procedure init;
var
i:longint;
begin
readln(n);
for i:=1 to n do
read(b[i]);
end;

procedure main;
var
i,j:longint;
x,y:int64;
begin
a[0]:=1; a[1]:=1;
for i:=1 to n do
begin
if b[i]-b[i-1]=0 then continue;
if b[i]-b[i-1]=1 then
begin
x:=0; y:=2*i-1-2*b[i-1];
for j:=1 to a[0] do
begin
x:=x+a[j]*y;
a[j]:=x mod mo;
x:=x div mo;
end;
while x>0 do
begin
inc(a[0]);
a[a[0]]:=x mod mo;
x:=x div mo;
end;
end;
if b[i]-b[i-1]=2 then
begin
x:=0; y:=sqr((i-1-b[i-1]));
for j:=1 to a[0] do
begin
x:=x+a[j]*y;
a[j]:=x mod mo;
x:=x div mo;
end;
while x>0 do
begin
inc(a[0]);
a[a[0]]:=x mod mo;
x:=x div mo;
end;
end;
end;
end;

procedure print;
var
i,l:longint;
ss:string;
begin
write(a[a[0]]);
for i:=a[0]-1 downto 1 do
begin
str(a[i],ss);
l:=length(ss);
while l<8 do
begin
inc(l);
write('0');
end;
write(a[i]);
end;
end;

begin
init;
main;
print;
end.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  jzoj1283