#include "bits/stdc++.h"
using namespace std;
#define REP(i, n) for(ll i = 0;i < n;i++)
#define ll long long
#define MOD 998244353LL
using vi = vector<ll>; // intの1次元の型に vi という別名をつける
using vvi = vector<vi>; // intの2次元の型に vvi という別名をつける
using vvvi = vector<vvi>; // intの2次元の型に vvi という別名をつける
const ll llMAX=9223372036854775807LL; 
const ll llMIN=-9223372036854775808LL;


//union find
struct UnionFind {
  vi col;
  map<ll, ll> nums;//[チーム番号]=そのチームに属する数
  UnionFind (ll n) {
    col.resize(n);
    for(ll i=0;i<n;i++)
      col[i]=i;
  }

  //ll root(ll x) { return parent[x] < 0 ? x : parent[x] = root(parent[x]); }
  ll douf(ll pid){
    if (col[pid]==pid){
      return pid;
    }else{
      col[pid]=douf(col[pid]);
      return col[pid];
    }
  }

  void merge(ll a, ll b) {
    if ( douf(a)>douf(b) )swap(a,b);
    col[douf(b)]=douf(a);
  }

  void finish(){
    for(ll i=0;i<col.size();i++){
      col[i]=douf(i);
      nums[col[i]]++;
    }
  }
};



ll n,k;
int main() {
  int ans=0;
  cin>>n>>k;
  UnionFind uf(n);
  UnionFind uf2(n);
  vvi a(n, vi(n));
  REP(i,n)REP(j,n)cin>>a[i][j];

  for(ll i=0;i<n;i++){
    for(ll ii=0;ii<i;ii++){
      bool flag=true;
      for(ll j=0;j<n;j++){
        if (a[i][j]+a[ii][j]>k)flag=false;
      }
      if (flag==true){
        uf.merge(i,ii);
      }
    }
  }
  
  for(ll i=0;i<n;i++){
    for(ll ii=0;ii<i;ii++){
      bool flag=true;
      for(ll j=0;j<n;j++){
        if (a[j][i]+a[j][ii]>k)flag=false;
      }
      if (flag==true){
        uf2.merge(i,ii);
      }
    }
  }

  uf.finish();
  uf2.finish();
  ans=1;
  for(auto it:uf.nums){
    for(ll j=1;j<=it.second;j++)
      ans=ans*j%MOD;
  }
  for(auto it:uf2.nums){
    for(ll j=1;j<=it.second;j++)
      ans=ans*j%MOD;
  }
 
  cout<<ans<<endl;
  return 0;
}
#include "bits/stdc++.h"
#define int long long
#define endl '\n'
using namespace std;
 
typedef long long ll;
#define db(x) cerr << #x << ": " << x << '\n';
#define read(a) int a; cin >> a;
#define readb(a, b) int a, b; cin >> a >> b;
#define readc(a, b, c) int a, b, c; cin >> a >> b >> c;
#define readarr(a, n) int a[(n) + 1] = {}; FOR(i, 1, (n)) {cin >> a[i];}
#define readmat(a, n, m) int a[n + 1][m + 1] = {}; FOR(i, 1, n) {FOR(j, 1, m) cin >> a[i][j];}
 
#define print(a) cout << a << endl;
#define printarr(a, n) FOR (i, 1, n) cout << a[i] << " "; cout << endl;
#define printv(v) for (int i: v) cout << i << " "; cout << endl;
#define printmat(a, n, m) FOR (i, 1, n) {FOR (j, 1, m) cout << a[i][j] << " "; cout << endl;} cout << endl;
#define all(v) v.begin(), v.end()
#define sz(v) (int)(v.size())
#define rz(v, n) v.resize((n) + 1);
#define pb push_back
#define fi first
#define se second
#define vi vector <int>
#define pi pair <int, int>
#define vpi vector <pi>
#define vvi vector <vi>
#define FOR(i, a, b) for (int i = (a); i <= (b); i++)
#define FORD(i, a, b) for (int i = (a); i >= (b); i--)
const ll inf = 1e18;
const ll mod = 998244353;
const ll N = 3e5 + 1;
mt19937 rng(chrono::steady_clock::now().time_since_epoch().count());

int n, m;
vi adj[N];
int f[N], vis[N];

void input()
{
	cin >> n;
	FOR (i, 1, n) cin >> f[i];
	FOR (i, 1, n)
	{
		//int x, y;
		//cin >> x >> y;
		adj[i].pb(f[i]);
		adj[f[i]].pb(i);
	}
}

void dfs (int cur = 1)
{
    vis[cur] = 1;
	for (int i: adj[cur])
		if (!vis[i])
			dfs(i);
}

int power (int a, int b = mod - 2)
{
    int res = 1;
    while (b > 0) {
        if (b & 1)
            res = res * a % mod;
        a = a * a % mod;
        b >>= 1;
    }
    return res;
}

signed main()
{
	ios_base::sync_with_stdio(false);
	cin.tie(0);	
	input();
	
	int cnt = 0;
	FOR (i, 1, n)
	    if (!vis[i])
	        dfs(i), cnt++;
    
    int ans = (power(2, cnt) - 1 + mod) % mod;
    print(ans);
}



