Theory NetCheck
section ‹Checking for Valid Network›
theory NetCheck
imports 
  "Lib/Refine_Add_Fofu"
  Network
  Graph_Impl
  DFS_Framework.Reachable_Nodes
begin
text ‹
  This theory contains code to read a network from an edge list, 
  and verify that the network is a valid input for the 
  Edmonds Karp Algorithm.
›
  declare [[coercion_delete int]]
  declare [[coercion_delete "real::nat⇒real"]]
  subsection ‹Graphs as Lists of Edges›
  text ‹Graphs can be represented as lists of edges, each edge being a triple of 
    start node, end node, and capacity. Capacities must be positive, and there
    must not be multiple edges with the same start and end node. ›
  type_synonym edge_list = "(node × node × capacity_impl) list"
  definition ln_invar :: "edge_list ⇒ bool" where 
    "ln_invar el ≡ 
      distinct (map (λ(u, v, _). (u,v)) el) 
    ∧ (∀(u,v,c)∈set el. c>0) 
    "
  definition ln_α :: "edge_list ⇒ capacity_impl graph" where 
    "ln_α el ≡ λ(u,v). 
      if ∃c. (u, v, c) ∈ set el ∧ c ≠ 0 then 
        SOME c. (u, v, c) ∈ set el ∧ c ≠ 0
      else 0"
  definition "ln_rel ≡ br ln_α ln_invar"
  
  lemma ln_equivalence: "(el, c') ∈ ln_rel ⟷ ln_invar el ∧ c' = ln_α el"
    unfolding ln_rel_def br_def by auto 
  definition ln_N :: "(node×node×_) list ⇒ nat" 
    
    where "ln_N el ≡ Max ((fst`set el) ∪ ((fst o snd)`set el)) + 1"
  lemma ln_α_imp_in_set: "⟦ln_α el (u,v)≠(0)⟧ ⟹ (u,v,ln_α el (u,v))∈set el"
    apply (auto simp: ln_α_def split: if_split_asm)
    apply (metis (mono_tags, lifting) someI_ex)
    done
  lemma ln_N_correct: "Graph.V (ln_α el) ⊆ {0..<ln_N el}"  
    apply (clarsimp simp: Graph.V_def Graph.E_def)
    apply (safe dest!: ln_α_imp_in_set)
    apply (fastforce simp: ln_N_def less_Suc_eq_le intro: Max_ge)
    apply (force simp: ln_N_def less_Suc_eq_le intro: Max_ge)
    done
  subsection ‹Pre-Networks›  
  text ‹This data structure is used to convert an edge-list to a network and 
    check validity. It maintains additional information, like a adjacency maps. ›