@@ -114,7 +114,7 @@ fn count(
114114 if !flower. contains ( u) || !flower. contains ( v) {
115115 break ;
116116 }
117- assert ! ( size > separator. len( ) ) ; // TODO: maybe equality can occur
117+ assert ! ( size > separator. len( ) ) ; // TODO: potentially, equality can occur
118118 forbidden_sizes. push ( size - separator. len ( ) ) ;
119119 }
120120 let phi = combinatorics:: rho ( & forbidden_sizes, memoization) ;
@@ -147,12 +147,26 @@ fn count(
147147}
148148
149149pub fn count_amos ( g : & Graph ) -> BigUint {
150- //if g.m == g.n-1 { return Integer::from(g.n); }
151- //if g.m == g.n { return Integer::from(2*g.n); }
152- //let num_possible_edges = g.n * (g.n - 1) / 2;
153- //if g.m == num_possible_edges - 2 { return (g.n * (g.n-1) - 4) * combinatorics::factorial(g.n-3, &mut Memoization::new(0, g.n)); }
154- //if g.m == num_possible_edges - 1 { return (2 * g.n - 3) * combinatorics::factorial(g.n-2, &mut Memoization::new(0, g.n)); }
155- //if g.m == num_possible_edges { return combinatorics::factorial(g.n, &mut Memoization::new(0, g.n)); }
150+ // some special cases, which can be handled immediately
151+ // see Thm 3 in https://jmlr.org/papers/v16/he15a.html
152+ if g. m == g. n - 1 {
153+ return BigUint :: from ( g. n ) ;
154+ }
155+ if g. m == g. n {
156+ return BigUint :: from ( 2 * g. n ) ;
157+ }
158+ let num_possible_edges = g. n * ( g. n - 1 ) / 2 ;
159+ if g. m == num_possible_edges - 2 {
160+ return ( g. n * ( g. n - 1 ) - 4 )
161+ * combinatorics:: factorial ( g. n - 3 , & mut vec ! [ BigUint :: ZERO ; g. n + 1 ] ) ;
162+ }
163+ if g. m == num_possible_edges - 1 {
164+ return ( 2 * g. n - 3 )
165+ * combinatorics:: factorial ( g. n - 2 , & mut vec ! [ BigUint :: ZERO ; g. n + 1 ] ) ;
166+ }
167+ if g. m == num_possible_edges {
168+ return combinatorics:: factorial ( g. n , & mut vec ! [ BigUint :: ZERO ; g. n + 1 ] ) ;
169+ }
156170
157171 // compute the clique tree of G
158172 let clique_tree = CliqueTree :: from ( g) ;
0 commit comments