Chỉ dùng lời giải này khi không có ý tưởng, và đừng copy-paste code từ lời giải này. Hãy tôn trọng người ra đề và người viết lời giải.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban. Lưu ý: Các code mẫu dưới đây chỉ mang tính tham khảo và có thể không AC được bài tập này Code mẫu của flashmt
const fi='';fo='';
maxn=40;
maxc=1048575;
var n,re,m,mid,max,num:longint;
v,w:array[1..40] of longint;
f,g:array[0..maxc] of longint;
procedure rf;
var i:longint;
begin
read(n,m);
for i:=1 to n do read(w[i],v[i]);
end;
procedure calc;
var i,j:longint;
begin
max:=1 shl mid-1;
for i:=1 to max do
for j:=0 to mid-1 do
if (i shr j) and 1=1 then
begin
f[i]:=f[i]+w[j+1];
g[i]:=g[i]+v[j+1];
end;
end;
procedure sort(l,r:longint);
var i,j,x,y,t:longint;
begin
i:=l; j:=r; x:=f[(i+j) shr 1]; y:=g[(i+j) shr 1];
repeat
while (f[i]<x) or ((f[i]=x) and (g[i]>y)) do i:=i+1;
while (f[j]>x) or ((f[j]=x) and (g[j]<y)) do j:=j-1;
if i<=j then
begin
t:=f[i]; f[i]:=f[j]; f[j]:=t;
t:=g[i]; g[i]:=g[j]; g[j]:=t;
i:=i+1; j:=j-1;
end;
until i>j;
if i<r then sort(i,r);
if l<j then sort(l,j);
end;
procedure edit;
var i:longint;
begin
num:=0;
for i:=1 to max do
if g[i]>g[num] then
begin
num:=num+1;
f[num]:=f[i];
g[num]:=g[i];
end;
end;
function bs(t:longint):longint;
var l,r,md,i:longint;
begin
l:=0; r:=num;
while l<=r do
begin
md:=(l+r) shr 1;
if f[md]=t then break;
if f[md]<t then l:=md+1
else r:=md-1;
end;
if f[md]=t then bs:=md
else
begin
for i:=md+1 downto md-1 do
if (i>=0) and (i<=num) and (f[i]<=t) then
begin
bs:=i; exit;
end;
end;
end;
procedure pr;
var i,l,ww,vv,j,x:longint;
begin
mid:=(n+1) shr 1;
calc;
sort(1,max);
edit;
l:=mid+1; mid:=n-mid;
max:=1 shl mid-1;
re:=0;
for i:=0 to max do
begin
ww:=0; vv:=0;
for j:=0 to mid-1 do
if (i shr j) and 1=1 then
begin
ww:=ww+w[l+j];
vv:=vv+v[l+j];
end;
if ww<=m then
begin
x:=bs(m-ww);
if vv+g[x]>re then re:=vv+g[x];
end;
end;
end;
procedure wf;
begin
writeln(re);
end;
begin
assign(input,fi); reset(input);
assign(output,fo); rewrite(output);
rf;
pr;
wf;
close(input); close(output);
end.
Code mẫu của RR
{$MODE OBJFPC}uses math;
const
FINP = '';
FOUT = '';
MAXN = 40;
var
f1,f2 : text;
n,m : longint;
res : int64;
v,w : array[1..MAXN] of longint;
n1,n2 : longint;
sv1,sv2,
sw1,sw2 : array[0..1050000] of longint;
procedure inp;
var
i:longint;
begin
read(f1,n,m);
for i:=1 to n do
read(f1,w[i],v[i]);
end;
procedure swap(var a,b:longint); inline;
var
tmp:longint;
begin
tmp:=a; a:=b; b:=tmp;
end;
procedure sort1(l,r:longint); inline;
var
i,j,mid:longint;
begin
i:=l; j:=r; mid:=sw1[l+random(r-l+1)];
repeat
while sw1[i]<mid do inc(i);
while sw1[j]>mid do dec(j);
if i<=j then
begin
swap(sv1[i],sv1[j]);
swap(sw1[i],sw1[j]);
inc(i); dec(j);
end;
until i>j;
if i<r then sort1(i,r);
if l<j then sort1(l,j);
end;
procedure sort2(l,r:longint); inline;
var
i,j,mid:longint;
begin
i:=l; j:=r; mid:=sw2[l+random(r-l+1)];
repeat
while sw2[i]<mid do inc(i);
while sw2[j]>mid do dec(j);
if i<=j then
begin
swap(sv2[i],sv2[j]);
swap(sw2[i],sw2[j]);
inc(i); dec(j);
end;
until i>j;
if i<r then sort2(i,r);
if l<j then sort2(l,j);
end;
procedure solve;
var
i,j,bit,nn,m1:longint;
begin
nn:=n shr 1;
n1:=1 shl nn;
n2:=1 shl (n-nn);
for i:=0 to n1-1 do
for bit:=1 to nn do
if (i shr (bit-1)) and 1=1 then
begin
inc(sv1[i],v[bit]);
inc(sw1[i],w[bit]);
end;
for i:=0 to n2-1 do
for bit:=1 to n-nn do
if (i shr (bit-1)) and 1=1 then
begin
inc(sv2[i],v[bit+nn]);
inc(sw2[i],w[bit+nn]);
end;
sort1(0,n1-1);
sort2(0,n2-1);
j:=0; res:=0; m1:=sv1[j];
for i:=n2-1 downto 0 do
begin
while (j<n1-1) and (sw1[j+1]+sw2[i]<=m) do
begin
inc(j);
m1:=max(m1,sv1[j]);
end;
if (sw1[j]+sw2[i]<=m) and (m1+sv2[i]>res) then res:=m1+sv2[i];
end;
writeln(f2,res);
end;
begin
assign(f1,FINP); reset(f1);
assign(f2,FOUT); rewrite(f2);
inp;
solve;
close(f1); close(f2);
end.
|