线段_线段树

题目大意

  把例2稍加改动,规定:线段的颜色可以相同。连续的相同颜色被视作一段。问x轴被分成多少段。

 

分析

  仍然定义cover如下:cover=-1表示该区间由多种颜色组成。cover>=0表示该区间只有一种单一的颜色cover。

  但是,统计算法就要做一下大的改动:

  如果当前子树的左子树的最右边的颜色等于右子树的最左边的颜色,且不等于颜色0,那代表有两条相连的段是同一种颜色组成的(是一段),那总段数-1(因为计算左右子树时多

计算了一次)。然而并没有关于此题的数据。测试什么的也不知道对不对(囧)。

 

源代码/pas:

 

type
tree=record
  l,r,c:longint;
end;
var
  t:array[1..1000]of tree;
procedure maketree(f:longint);
var
  mid:longint;
begin
  if t[f].l<>t[f].r-1 then
  begin
    mid:=(t[f].l+t[f].r)div 2;
    t[f*2].l:=t[f].l;
    t[f*2].r:=mid;
    t[f*2+1].l:=mid;
    t[f*2+1].r:=t[f].r;
    maketree(f*2);
    maketree(f*2+1);
  end;
end;
procedure insert(f,x,y,color:longint);
var
  mid:longint;
begin
  if t[f].c<>color then
  begin
    mid:=(t[f].l+t[f].r)div 2;
    if (t[f].l=x)and(t[f].r=y) then t[f].c:=color
    else
    begin
      if t[f].c<>-1 then
      begin
        t[f*2].c:=t[f].c;
        t[f*2+1].c:=t[f].c;
        t[f].c:=-1;
      end;
      if (y<=mid) then
      insert(f*2,x,y,color)
      else
      if (x>=mid) then
      insert(f*2+1,x,y,color)
      else
      begin
        insert(f*2,x,mid,color);
        insert(f*2+1,mid,y,color);
      end;
    end;
  end;
end;
function count(f:longint;var x,y:longint):longint;
var
  re,tl,tr:longint;
begin
  if t[f].c<>-1 then
  begin
    x:=t[f].c;
    y:=x;
    if t[f].c>0 then
    count:=1
    else
    count:=0;
  end
  else
  if t[f].r-t[f].l>1 then
  begin
    re:=count(f*2,x,tl)+count(f*2+1,tr,y);
    if (tl=tr)and(tl<>-1) then
    re:=re-1;
    count:=re;
  end;
end;
procedure init;
var n,m,x,y,i,u,v,co:longint;
begin
  readln(m,n);
  t[1].l:=1;
  t[1].r:=n;
  maketree(1);
  for i:=1 to m do
  begin
    readln(u,v,co);
    insert(1,u,v,co);
  end;
  writeln(count(1,x,y));
end;
begin
  init;
end.


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值