Problem:
Score : 100 points

Problem Statement

There is a simple directed graph G with N vertices, numbered 1, 2, \ldots, N.

For each i and j (1 \leq i, j \leq N), you are given an integer a_{i, j} that represents whether there is a directed edge from Vertex i to j.
If a_{i, j} = 1, there is a directed edge from Vertex i to j; if a_{i, j} = 0, there is not.

Find the number of different directed paths of length K in G, modulo 10^9 + 7.
We will also count a path that traverses the same edge multiple times.

Constraints

All values in input are integers.

1 \leq N \leq 50

1 \leq K \leq 10^{18}

a_{i, j} is 0 or 1.

a_{i, i} = 0

Input

Input is given from Standard Input in the following format:

N K
a_{1, 1} \ldots a_{1, N}
:
a_{N, 1} \ldots a_{N, N}

Output

Print the number of different directed paths of length K in G, modulo 10^9 + 7.

Sample Input 1

4 2
0 1 0 0
0 0 1 1
0 0 0 1
1 0 0 0

Sample Output 1

6

G is drawn in the figure below:

There are six directed paths of length 2:

1 → 2 → 3

1 → 2 → 4

2 → 3 → 4

2 → 4 → 1

3 → 4 → 1

4 → 1 → 2

Sample Input 2

3 3
0 1 0
1 0 1
0 0 0

Sample Output 2

3

G is drawn in the figure below:

There are three directed paths of length 3:

1 → 2 → 1 → 2

2 → 1 → 2 → 1

2 → 1 → 2 → 3

Sample Input 3

6 2
0 0 0 0 0 0
0 0 1 0 0 0
0 0 0 0 0 0
0 0 0 0 1 0
0 0 0 0 0 1
0 0 0 0 0 0

Sample Output 3

1

G is drawn in the figure below:

There is one directed path of length 2:

4 → 5 → 6

Sample Input 4

1 1
0

Sample Output 4

0

Sample Input 5

10 1000000000000000000
0 0 1 1 0 0 0 1 1 0
0 0 0 0 0 1 1 1 0 0
0 1 0 0 0 1 0 1 0 1
1 1 1 0 1 1 0 1 1 0
0 1 1 1 0 1 0 1 1 1
0 0 0 1 0 0 1 0 1 0
0 0 0 1 1 0 0 1 0 1
1 0 0 0 1 0 1 0 0 0
0 0 0 0 0 1 0 0 0 0
1 0 1 1 1 0 1 1 1 0

Sample Output 5

957538352

Be sure to print the count modulo 10^9 + 7.

Solution in Rust (1.15.1) (judge verdict: Accepted)

#![allow(non_snake_case, unused)]
use std::collections::*;

////////// missing functions in 1.15.1 //////////
macro_rules! eprint {
	($($t:tt)*) => {{
		use ::std::io::Write;
		let _ = write!(::std::io::stderr(), $($t)*);
	}};
}
macro_rules! eprintln {
	() => { eprintln!(""); };
	($($t:tt)*) => {{
		use ::std::io::Write;
		let _ = writeln!(::std::io::stderr(), $($t)*);
	}};
}
macro_rules! dbg {
	($v:expr) => {{
		let val = $v;
		eprintln!("[{}:{}] {} = {:?}", file!(), line!(), stringify!($v), val);
		val
	}}
}
/////////////////////////////////////////////////
pub trait SetMinMax {
	fn setmin(&mut self, v: Self) -> bool;
	fn setmax(&mut self, v: Self) -> bool;
}
impl<T> SetMinMax for T where T: PartialOrd {
	fn setmin(&mut self, v: T) -> bool {
		*self > v && { *self = v; true }
	}
	fn setmax(&mut self, v: T) -> bool {
		*self < v && { *self = v; true }
	}
}

macro_rules! mat {
	($($e:expr),*) => { Vec::from(vec![$($e),*]) };
	($($e:expr,)*) => { Vec::from(vec![$($e),*]) };
	($e:expr; $d:expr) => { Vec::from(vec![$e; $d]) };
	($e:expr; $d:expr $(; $ds:expr)+) => { Vec::from(vec![mat![$e $(; $ds)*]; $d]) };
}

pub fn readln() -> String {
	let mut line = String::new();
	::std::io::stdin().read_line(&mut line).unwrap_or_else(|e| panic!("{}", e));
	line
}

macro_rules! read {
	($($t:tt),*; $n:expr) => {{
		let stdin = ::std::io::stdin();
		let ret = ::std::io::BufRead::lines(stdin.lock()).take($n).map(|line| {
			let line = line.unwrap();
			let mut it = line.split_whitespace();
			_read!(it; $($t),*)
		}).collect::<Vec<_>>();
		ret
	}};
	($($t:tt),*) => {{
		let line = readln();
		let mut it = line.split_whitespace();
		_read!(it; $($t),*)
	}};
}

macro_rules! _read {
	($it:ident; [char]) => {
		_read!($it; String).chars().collect::<Vec<_>>()
	};
	($it:ident; [u8]) => {
		Vec::from(_read!($it; String).into_bytes())
	};
	($it:ident; [$t:ty]) => {
		$it.map(|s| s.parse::<$t>().unwrap_or_else(|e| panic!("{}", e))).collect::<Vec<_>>()
	};
	($it:ident; $t:ty) => {
		$it.next().unwrap_or_else(|| panic!("input mismatch")).parse::<$t>().unwrap_or_else(|e| panic!("{}", e))
	};
	($it:ident; $($t:tt),+) => {
		($(_read!($it; $t)),*)
	};
}

pub fn main() {
	let _ = ::std::thread::Builder::new().name("run".to_string()).stack_size(32 * 1024 * 1024).spawn(run).unwrap().join();
}


use std::ops::*;
use std::marker::PhantomData;

pub trait Int {
	fn as_i32(self) -> i32;
	fn as_i64(self) -> i64;
	fn as_u32(self) -> u32;
	fn as_u64(self) -> u64;
	fn as_usize(self) -> usize;
}

macro_rules! impl_int {
	() => {};
	($t:ty $(, $ts:ty)*) => {
		impl Int for $t {
			fn as_i32(self) -> i32 {
				self as i32
			}
			fn as_i64(self) -> i64 {
				self as i64
			}
			fn as_u32(self) -> u32 {
				self as u32
			}
			fn as_u64(self) -> u64 {
				self as u64
			}
			fn as_usize(self) -> usize {
				self as usize
			}
		}
		impl_int!($($ts),*);
	}
}

impl_int!(i8, i16, i32, i64, u8, u16, u32, u64, isize, usize);

pub trait Mod: Copy + Default + Ord {
	fn m() -> u32;
}

#[derive(Clone, Copy, Default, Hash, PartialEq, PartialOrd, Eq, Ord)]
pub struct ModP<M>(pub u32, PhantomData<M>);

impl<M> ::std::fmt::Debug for ModP<M> {
	fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result {
		self.0.fmt(f)
	}
}

impl<M> ::std::fmt::Display for ModP<M> {
	fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result {
		self.0.fmt(f)
	}
}

impl<M: Mod> ModP<M> {
	/// Assume 0 <= a < m.
	pub fn new<I: Int>(a: I) -> ModP<M> {
		ModP(a.as_u32(), PhantomData)
	}
	pub fn pow<I: Int>(&self, b: I) -> ModP<M> {
		let mut b = b.as_i64();
		if b < 0 {
			b = b % (M::m() - 1) as i64 + M::m() as i64 - 1;
		}
		let mut res = ModP::new(1);
		let mut a = *self;
		while b > 0 {
			if (b & 1) > 0 { res *= a; }
			a *= a;
			b >>= 1;
		}
		res
	}
	pub fn inv(&self) -> ModP<M> {
		self.pow(M::m() as u64 - 2)
	}
}

impl<'a, M: Mod> Add for &'a ModP<M> {
	type Output = ModP<M>;
	fn add(self, a: &ModP<M>) -> ModP<M> {
		let v = self.0 + a.0;
		if v >= M::m() { ModP::new(v - M::m()) } else { ModP::new(v) }
	}
}

impl<'a, M: Mod> Sub for &'a ModP<M> {
	type Output = ModP<M>;
	fn sub(self, a: &ModP<M>) -> ModP<M> {
		if self.0 < a.0 { ModP::new(M::m() - a.0 + self.0) } else { ModP::new(self.0 - a.0 ) }
	}
}

impl<'a, M: Mod> Mul for &'a ModP<M> {
	type Output = ModP<M>;
	fn mul(self, a: &ModP<M>) -> ModP<M> {
		ModP::new(((self.0 as u64 * a.0 as u64) % M::m() as u64) as u32)
	}
}

impl<'a, M: Mod> Div for &'a ModP<M> {
	type Output = ModP<M>;
	fn div(self, a: &ModP<M>) -> ModP<M> {
		self * a.inv()
	}
}

impl<'a, M: Mod> Neg for &'a ModP<M> {
	type Output = ModP<M>;
	fn neg(self) -> ModP<M> {
		ModP::new(if self.0 == 0 { 0 } else { M::m() - self.0 })
	}
}

impl<M: Mod> Neg for ModP<M> {
	type Output = ModP<M>;
	fn neg(self) -> ModP<M> {
		(&self).neg()
	}
}

macro_rules! impl_all {
	($t:ident$(<$($g:ident),*>)*; $Op:ident:$op:ident:$Opa:ident:$opa:ident) => {
		impl<$($($g),*)*> $Op for $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			type Output = $t$(<$($g),*>)*;
			fn $op(self, a: $t$(<$($g),*>)*) -> $t$(<$($g),*>)* { (&self).$op(&a) }
		}
		impl<'a, $($($g),*)*> $Op<&'a $t$(<$($g),*>)*> for $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			type Output = $t$(<$($g),*>)*;
			fn $op(self, a: &$t$(<$($g),*>)*) -> $t$(<$($g),*>)* { (&self).$op(&a) }
		}
		impl<'a, $($($g),*)*> $Op<$t$(<$($g),*>)*> for &'a $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			type Output = $t$(<$($g),*>)*;
			fn $op(self, a: $t$(<$($g),*>)*) -> $t$(<$($g),*>)* { (&self).$op(&a) }
		}
		impl<$($($g),*)*> $Opa for $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			fn $opa(&mut self, a: $t$(<$($g),*>)*) { *self = (&*self).$op(&a) }
		}
	}
}

impl_all!(ModP<M>; Add:add:AddAssign:add_assign);
impl_all!(ModP<M>; Sub:sub:SubAssign:sub_assign);
impl_all!(ModP<M>; Mul:mul:MulAssign:mul_assign);
impl_all!(ModP<M>; Div:div:DivAssign:div_assign);

#[macro_export]
macro_rules! define_mod {
	($name:ident; $e:expr) => {
		#[derive(Clone, Copy, Default, Hash, PartialEq, PartialOrd, Eq, Ord)]
		pub struct _Mod;
		pub type $name = $crate::ModP<_Mod>;
		impl $crate::Mod for _Mod {
			fn m() -> u32 { $e }
		}
	}
}

impl<M: Mod, I: Int> From<I> for ModP<M> {
	/// Assume 0 <= a < m.
	fn from(a: I) -> ModP<M> { ModP::new(a) }
}

#[derive(Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)]
pub struct Mat<T>(pub Vec<Vec<T>>);

impl<T> Mat<T> where T: Clone + Default {
	pub fn row(a: Vec<T>) -> Mat<T> { Mat(vec![a]) }
	pub fn col(a: Vec<T>) -> Mat<T> { Mat(a.into_iter().map(|v| vec![v]).collect()) }
	pub fn to_vec(&self) -> Vec<T> {
		if self.len() == 1 {
			self[0].clone()
		} else if self[0].len() == 1 {
			self.iter().map(|r| r[0].clone()).collect()
		} else {
			panic!("Cannot transform Mat into Vec. row: {}, col: {}", self.len(), self[0].len());
		}
	}
	pub fn transpose(&self) -> Mat<T> {
		let mut v = vec![Vec::with_capacity(self.len()); self[0].len()];
		for r in self.iter() {
			for (i, x) in r.iter().enumerate() {
				v[i].push(x.clone());
			}
		}
		Mat(v)
	}
	pub fn pow(&self, mut b: u64) -> Mat<T> where T: AddAssign + PartialEq + From<u8>, for<'b> &'b T: Mul<Output = T> {
		let n = self.len();
		assert_eq!(n, self[0].len());
		let mut res: Mat<T> = Mat(mat![0.into(); n; n]);
		for i in 0..n { res[i][i] = 1.into() }
		let mut a = self.clone();
		while b > 0 {
			if (b & 1) > 0 { res = &res * &a; }
			a = &a * &a;
			b >>= 1;
		}
		res
	}
}

impl<T> Deref for Mat<T> {
	type Target = Vec<Vec<T>>;
	#[inline]
	fn deref(&self) -> &Vec<Vec<T>> { &self.0 }
}

impl<T> DerefMut for Mat<T> {
	#[inline]
	fn deref_mut(&mut self) -> &mut Vec<Vec<T>> { &mut self.0 }
}

impl<'a, T> Add for &'a Mat<T> where for<'b> &'b T: Add<Output = T> {
	type Output = Mat<T>;
	fn add(self, a: &Mat<T>) -> Mat<T> {
		assert_eq!(self.len(), a.len());
		assert_eq!(self[0].len(), a[0].len());
		Mat(self.iter().zip(a.iter()).map(|(xs, ys)| xs.iter().zip(ys.iter()).map(|(x, y)| x + y).collect()).collect())
	}
}

impl<'a, T> Sub for &'a Mat<T> where for<'b> &'b T: Sub<Output = T> {
	type Output = Mat<T>;
	fn sub(self, a: &Mat<T>) -> Mat<T> {
		assert_eq!(self.len(), a.len());
		assert_eq!(self[0].len(), a[0].len());
		Mat(self.iter().zip(a.iter()).map(|(xs, ys)| xs.iter().zip(ys.iter()).map(|(x, y)| x - y).collect()).collect())
	}
}

impl<'a, T> Mul for &'a Mat<T> where T: Clone + Default + AddAssign + PartialEq, for<'b> &'b T: Mul<Output = T> {
	type Output = Mat<T>;
	/// 疎行列に対応．n×k行列Aとk×m行列Bの積を O(#nonzero(A) m)で行う．
	fn mul(self, a: &Mat<T>) -> Mat<T> {
		assert_eq!(self[0].len(), a.len());
		let zero = T::default();
		let mut b = mat![zero.clone(); self.len(); a[0].len()];
		for (i, si) in self.iter().enumerate() {
			for (k, sik) in si.iter().enumerate() {
				if *sik != zero {
					for (bij, akj) in b[i].iter_mut().zip(a[k].iter()) {
						*bij += sik * akj;
					}
				}
			}
		}
		Mat(b)
	}
}

macro_rules! impl_all {
	($t:ident$(<$($g:ident),*>)*; $Op:ident:$op:ident:$Opa:ident:$opa:ident) => {
		impl<$($($g),*)*> $Op for $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			type Output = $t$(<$($g),*>)*;
			#[inline]
			fn $op(self, a: $t$(<$($g),*>)*) -> $t$(<$($g),*>)* { (&self).$op(&a) }
		}
		impl<'a, $($($g),*)*> $Op<&'a $t$(<$($g),*>)*> for $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			type Output = $t$(<$($g),*>)*;
			#[inline]
			fn $op(self, a: &$t$(<$($g),*>)*) -> $t$(<$($g),*>)* { (&self).$op(&a) }
		}
		impl<'a, $($($g),*)*> $Op<$t$(<$($g),*>)*> for &'a $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			type Output = $t$(<$($g),*>)*;
			#[inline]
			fn $op(self, a: $t$(<$($g),*>)*) -> $t$(<$($g),*>)* { (&self).$op(&a) }
		}
		impl<$($($g),*)*> $Opa for $t$(<$($g),*>)* where for<'b> &'b $t$(<$($g),*>)*: $Op<Output = $t$(<$($g),*>)*> {
			#[inline]
			fn $opa(&mut self, a: $t$(<$($g),*>)*) { *self = (&*self).$op(&a) }
		}
	}
}

impl_all!(Mat<T>; Add:add:AddAssign:add_assign);
impl_all!(Mat<T>; Sub:sub:SubAssign:sub_assign);
impl_all!(Mat<T>; Mul:mul:MulAssign:mul_assign);

fn run() {
	define_mod!(P; 1_000_000_007);
	let (N, K) = read!(usize, u64);
	let a = read!([u32]; N);
	let a = Mat(a.into_iter().map(|a| a.into_iter().map(P::new).collect()).collect());
	let a = a.pow(K);
	let mut tot = P::new(0);
	for i in 0..N {
		for j in 0..N {
			tot += a[i][j];
		}
	}
	println!("{}", tot);
}