图的最大流-前置推送标签方法
  TEZNKK3IfmPf 2023年11月15日 18 0
 package com.data.struct;



public class RelabelToFront {
  private Node[][]graphic;
  private Node s;
  private Node t;
  public RelabelToFront(){
    graphic=new Node[6][6];
    Node node0=new Node();
    node0.start=0;
    node0.end=0;
    graphic[0][0]=node0;
    Node node1=new Node();
    node1.start=1;
    node1.end=1;
    graphic[1][1]=node1;
    Node node2=new Node();
    node2.start=2;
    node2.end=2;
    graphic[2][2]=node2;
    Node node3=new Node();
    node3.start=3;
    node3.end=3;
    graphic[3][3]=node3;
    Node node4=new Node();
    node4.start=4;
    node4.end=4;
    graphic[4][4]=node4;
    Node node5=new Node();
    node5.start=5;
    node5.end=5;
    graphic[5][5]=node5;
    Node node01=new Node();
    node01.c=16;
    node01.start=0;
    node01.end=1;
    graphic[0][1]=node01;
    Node node10=new Node();
    node10.start=1;
    node10.end=0;
    node10.reverse=true;
    graphic[1][0]=node10;
    Node node02=new Node();
    node02.c=13;
    node02.start=0;
    node02.end=2;
    graphic[0][2]=node02;
    Node node20=new Node();
    node20.start=2;
    node20.end=0;
    node20.reverse=true;
    graphic[2][0]=node20;
    Node node13=new Node();
    node13.c=12;
    node13.start=1;
    node13.end=3;
    graphic[1][3]=node13;
    Node node31=new Node();
    node31.start=3;
    node31.end=1;
    node31.reverse=true;
    graphic[3][1]=node31;
    Node node21=new Node();
    node21.c=4;
    node21.start=2;
    node21.end=1;
    graphic[2][1]=node21;
    Node node12=new Node();
    node12.start=1;
    node12.end=2;
    node12.reverse=true;
    graphic[1][2]=node12;
    Node node24=new Node();
    node24.start=2;
    node24.end=4;
    node24.c=14;
    graphic[2][4]=node24;
    Node node42=new Node();
    node42.start=4;
    node42.end=2;
    node42.reverse=true;
    graphic[4][2]=node42;
    Node node32=new Node();
    node32.c=9;
    node32.start=3;
    node32.end=2;
    graphic[3][2]=node32;
    Node node23=new Node();
    node23.start=2;
    node23.end=3;
    node23.reverse=true;
    graphic[2][3]=node23;
    Node node35=new Node();
    node35.c=20;
    node35.start=3;
    node35.end=5;
    graphic[3][5]=node35;
    Node node53=new Node();
    node53.start=5;
    node53.end=3;
    node53.reverse=true;
    graphic[5][3]=node53;
    Node node43=new Node();
    node43.c=7;
    node43.start=4;
    node43.end=3;
    graphic[4][3]=node43;
    Node node34=new Node();
    node34.start=3;
    node34.end=4;
    node34.reverse=true;
    graphic[3][4]=node34;
    Node node45=new Node();
    node45.c=4;
    node45.start=4;
    node45.end=5;
    graphic[4][5]=node45;
    Node node54=new Node();
    node54.start=5;
    node54.end=4;
    node54.reverse=true;
    graphic[5][4]=node54;
    
    s=graphic[0][0];
    t=graphic[5][5];
  }
  
  public void relabelToFront(){
    initializePreflow();
    Node head=graphic[1][1];
    Node last=head;
    for(int i=2;i<graphic.length-1;i++){
      last.lnext=graphic[i][i];
      last=last.lnext;
    }
    for(int i=1;i<graphic.length-1;i++){
      Node lastN=graphic[i][i].N;
      for(int j=0;j<graphic.length;j++){
        if(i==j){
          continue;
        }
        if(lastN==null){
          if(graphic[i][j]!=null){
            Node node=graphic[j][j].clone();
            lastN=node;
            graphic[i][i].N=node;
          }
        }else{
          if(graphic[i][j]!=null){
            Node node=graphic[j][j].clone();
            lastN.next=node;
            lastN=lastN.next;
          }
          
        }
      }
      for(int j=0;j<graphic.length;j++){
        if(i==j){
          continue;
        }
        if(lastN==null){
          if(graphic[j][i]!=null){
            Node node=graphic[j][j].clone();
            lastN=node;
            graphic[i][i].N=node;
          }
        }else{
          if(graphic[j][i]!=null){
            Node node=graphic[j][j].clone();
            lastN.next=node;
            lastN=lastN.next;
          }
          
        }
      }
    }
    for(int i=1;i<graphic.length-1;i++){
      graphic[i][i].current=graphic[i][i].N;
    }
    Node u=head;
    Node prev=u;
    while(u!=null){
      int oldH=u.h;
      discharge(u);
      if(u.h>oldH){
        if(prev!=u){
          prev.lnext=u.lnext;
          u.lnext=head;
          head=u;
        }
      }
      prev=u;
      u=u.lnext;
    }
  }
  
  public void discharge(Node u){
    while(u.e>0){
      Node v=u.current;
      if(v==null){
        relabel(u);
        u.current=u.N;
      }else{
        Node vr=graphic[v.start][v.end];
        if(!graphic[u.start][v.start].reverse&&(graphic[u.start][v.start].c-graphic[u.start][v.start].f>0)&&u.h==vr.h+1){
          push(u,vr);
        }else if(graphic[u.start][v.start].reverse&&graphic[u.start][v.start].f>0&&u.h==vr.h+1){
          push(u,vr);
        }else{
          u.current=v.next;
        }
      }
    }
  }
  
  public void push(Node u,Node v){
    Node uv=graphic[u.start][v.start];
    Node vu=graphic[v.start][u.start];
    int delta=Integer.MAX_VALUE;
    if(!uv.reverse){
      delta=Math.min(delta, Math.min(u.e, uv.c-uv.f));
      uv.f=uv.f+delta;
      vu.f=uv.f;
    }else{
      delta=Math.min(delta, Math.min(u.e, uv.f));
      uv.f=uv.f-delta;
      vu.f=uv.f;
    }
    System.out.println("["+uv.start+","+uv.end+"]:"+delta);
    u.e=u.e-delta;
    v.e=v.e+delta;
    
  }
  public void relabel(Node u){
    int h=Integer.MAX_VALUE;
    for(int i=0;i<graphic.length;i++){
      if(u.start!=i&&graphic[u.start][i]!=null){
        if(!graphic[u.start][i].reverse){
          if(graphic[u.start][i].c-graphic[u.start][i].f>0){
            h=Math.min(h, graphic[i][i].h);
          }
        }else{
          if(graphic[i][u.start].f>0){
            h=Math.min(h, graphic[i][i].h);
          }
        }
      }
    }
    if(h==Integer.MAX_VALUE){
      return;
    }
    u.h=1+h;
    
  }
  public void initializePreflow(){
    s.h=graphic.length;
    for(int i=0;i<graphic.length;i++){
      if(i!=s.start&&graphic[s.start][i]!=null){
        graphic[s.start][i].f=graphic[s.start][i].c;
        graphic[i][s.start].f=graphic[s.start][i].c;
        graphic[i][i].e=graphic[s.start][i].c;
        s.e=s.e-graphic[s.start][i].c;
      }
    }
  }
  
  public void printE(){
    System.out.println("E:");
    for(int i=0;i<graphic.length;i++){
      for(int j=0;j<graphic.length;j++){
        if(graphic[i][j]!=null){
          System.out.print(graphic[i][j].e+" ");
        }else{
          System.out.print("  ");
        }
      }
      System.out.println();
    }
  }
  public void printF(){
    System.out.println("F:");
    for(int i=0;i<graphic.length;i++){
      for(int j=0;j<graphic.length;j++){
        if(graphic[i][j]!=null){
          System.out.print(graphic[i][j].f+" ");
        }else{
          System.out.print("  ");
        }
      }
      System.out.println();
    }
  }
  public void printH(){
    System.out.println("H:");
    for(int i=0;i<graphic.length;i++){
      for(int j=0;j<graphic.length;j++){
        if(graphic[i][j]!=null){
          System.out.print(graphic[i][j].h+" ");
        }else{
          System.out.print("  ");
        }
      }
      System.out.println();
    }
  }
  public void printResult(){
    int result=0;
    for(int i=0;i<graphic.length;i++){
      if(graphic[t.start][i]!=null){
        result+=graphic[i][t.start].f;
      }
    }
    System.out.println("max flow:"+result);
  }
  public void print(){
    for(int i=0;i<graphic.length;i++){
      for(int j=0;j<graphic.length;j++){
        if(graphic[i][j]!=null){
          System.out.print(graphic[i][j].c+" ");
        }else{
          System.out.print("  ");
        }
      }
      System.out.println();
    }
  }
  private class Node{
    private int c;
    private int f;
    private int start;
    private int end;
    private boolean reverse;
    private int e;
    private int h;
    private Node current;
    private Node next;
    private Node N;
    private Node lnext;
    public Node clone(){
      Node newNode=new Node();
      newNode.c=c;
      newNode.f=f;
      newNode.start=start;
      newNode.e=e;
      newNode.end=end;
      newNode.reverse=reverse;
      newNode.h=h;
      return newNode;
    }
  }
  public static void main(String[] args) {
    RelabelToFront r=new RelabelToFront();
    r.print();
    r.relabelToFront();
    r.printResult();

  }

}
【版权声明】本文内容来自摩杜云社区用户原创、第三方投稿、转载,内容版权归原作者所有。本网站的目的在于传递更多信息,不拥有版权,亦不承担相应法律责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@moduyun.com

  1. 分享:
最后一次编辑于 2023年11月15日 0

暂无评论

推荐阅读
  TEZNKK3IfmPf   2024年03月29日   50   0   0 i++
  TEZNKK3IfmPf   2023年11月15日   31   0   0 idei++
  TEZNKK3IfmPf   2023年11月15日   20   0   0 搜索i++
  TEZNKK3IfmPf   2024年03月29日   117   0   0 i++排序
TEZNKK3IfmPf