1627. Join

http://acm.timus.ru/problem.aspx?space=1&num=1627

给一个无向图,问可以有多少生成树 

参照     周冬《生成树的计数及其应用》

代码:

import java.io.File;

import java.io.FileNotFoundException;

import java.math.BigDecimal;

import java.math.BigInteger;

import java.util.Scanner;



class Fraction {

	public BigInteger x;

	public BigInteger y;



	public Fraction(int xx, int yy) {

		x = BigInteger.valueOf(xx);

		y = BigInteger.valueOf(yy);

	}



	static public BigInteger gcd(BigInteger x, BigInteger y) {

	

		if (x.mod(y).compareTo(BigInteger.ZERO) == 0) {

			return y;

		} else {

			return gcd(y, x.mod(y));

		}

	}



	public Fraction add(Fraction f) {

		Fraction ff = new Fraction(0, 1);

		ff.y = this.y.multiply(f.y);

		ff.x = this.x.multiply(f.y).add(this.y.multiply(f.x));

		BigInteger z = Fraction.gcd(ff.x, ff.y);

		ff.x = ff.x.divide(z);

		ff.y = ff.y.divide(z);

		return ff;

	}



	public Fraction subtract(Fraction f) {

		Fraction ff = new Fraction(0, 1);

		ff.y = this.y.multiply(f.y);

		ff.x = this.x.multiply(f.y).subtract(this.y.multiply(f.x));

		BigInteger z = Fraction.gcd(ff.x, ff.y);

		ff.x = ff.x.divide(z);

		ff.y = ff.y.divide(z);

		return ff;

	}



	public Fraction multiply(Fraction f) {

		Fraction ff = new Fraction(0, 1);

		ff.y = this.y.multiply(f.y);

		ff.x = this.x.multiply(f.x);

		BigInteger z = Fraction.gcd(ff.x, ff.y);

		ff.x = ff.x.divide(z);

		ff.y = ff.y.divide(z);

		return ff;

	}



	public Fraction divide(Fraction f) {

		Fraction ff = new Fraction(0, 1);

		ff.y = this.y.multiply(f.x);

		ff.x = this.x.multiply(f.y);

		BigInteger z = Fraction.gcd(ff.x, ff.y);

		ff.x = ff.x.divide(z);

		ff.y = ff.y.divide(z);

		if (ff.y.compareTo(BigInteger.ZERO) < 0) {

			ff.y = ff.y.abs();

			ff.x = ff.x.multiply(BigInteger.valueOf(-1L));

		}

		return ff;

	}



	public boolean equals(Fraction f) {

		if (this.x.equals(f.x) && this.y .equals(f.y)) {

			return true;

		}

		return false;

	}



}



public class Main {



	/**

	 * @param args

	 * @throws FileNotFoundException

	 */

	public static int N = 100;



	public static void main(String[] args) throws FileNotFoundException {

		// TODO Auto-generated method stub

		Scanner in = new Scanner(System.in);

		Fraction[][] a = new Fraction[N][N];



		for (int i = 0; i < N; ++i) {

			for (int j = 0; j < N; ++j) {

				a[i][j] = new Fraction(0, 1);

			}

		}

		int[][] k = new int[N][N];

		int[] X = { 0, 0, -1, 1 };

		int[] Y = { 1, -1, 0, 0 };



		int n = in.nextInt();

		int m = in.nextInt();

		int ln = 0;

		for (int i = 0; i < n; ++i) {

			String s = in.next();

			for (int j = 0; j < m; ++j) {

				if (s.charAt(j) == '.') {

					k[i][j] = (++ln);

				}

			}

		}

		for (int i = 0; i < n; ++i) {

			for (int j = 0; j < m; ++j) {

				if (k[i][j] > 0) {

					for (int w = 0; w < 4; ++w) {

						int x = i + X[w];

						int y = j + Y[w];

						if (x >= 0 && x < n && y >= 0 && y < m && k[x][y] > 0) {

							a[k[i][j]][k[x][y]] = new Fraction(-1, 1);

							a[k[i][j]][k[i][j]] = a[k[i][j]][k[i][j]]

									.add(new Fraction(1, 1));

						}

					}

				}

			}

		}

		if (ln > 1) {

			System.out.println(valueOfMatrix(a, ln - 1));

		}else{

			System.out.println(1);

		}

	}



	public static BigInteger valueOfMatrix(Fraction[][] a, int n) {

		// TODO Auto-generated method stub

		BigInteger MOD = BigInteger.valueOf(1000000000L);

		dfs(a, n);

		Fraction v = new Fraction(1, 1);

		for (int i = 1; i <= n; ++i) {

			v = v.multiply(a[i][i]);

		}

		return v.x.mod(MOD);

	}



	public static void dfs(Fraction[][] a, int n) {

		if (n == 1)

			return;

		int l = n;

		Fraction fractionZORE = new Fraction(0, 1);

		while (l >= 1 && a[l][n].equals(fractionZORE)) {

			--l;

		}

		if (l < 1) {

			dfs(a, n - 1);

		} else {

			if (l < n) {

				for (int j = 1; j <= n; ++j) {

					Fraction z = a[l][j];

					a[l][j] = a[n][j];

					a[n][j] = z;

				}

			}



			for (int i = 1; i < n; ++i) {

				if (!a[i][n].equals(fractionZORE)) {

					Fraction z = a[i][n].divide(a[n][n]);

					for (int j = 1; j <= n; ++j) {

						a[i][j] = a[i][j].subtract(a[n][j].multiply(z));

					}

				}

			}

			dfs(a, n - 1);

		}

	}



}

  

你可能感兴趣的:(JOIN)