Our claim is difficult to find a \ (E (\ max (S)) \) , it seems more difficult, so we direct the min-max-repellent capacity, if we enumerate a set of \ (T \) , collection \ (T \) there \ (t \) , then the contribution of neighboring lattice of the answer is \ ((- 1) ^ { | T | +1} \ frac {2nm-nm} {t} \)
So we do dp a shaped pressing contour, provided \ (dp_ {i, j, s, k} \) represents the current cell processed is \ ((I, J) \) , the contour line status \ (S \ ) , select the \ (k \) adjacent grid, you can transfer brush table
Code
#include<bits/stdc++.h>
#define re register
const int mod=998244353;
inline int dqm(int x) {return x<0?x+mod:x;}
inline int upd(int &x,int y) {x+=y;if(x>=mod)x-=mod;}
int dp[2][(1<<6)+1][1200],inv[1200],ans,n,m;
char ma[105][105];
int main() {
scanf("%d%d",&n,&m);int S=2*n*m-n-m,nS=0,len=(1<<n);--len;inv[1]=1;
for(re int i=2;i<=S;i++) inv[i]=1ll*(mod-mod/i)*inv[mod%i]%mod;
for(re int i=1;i<=n;i++) scanf("%s",ma[i]+1);
dp[0][0][0]=mod-1;int o=0;
for(re int i=1;i<=m;i++)
for(re int j=1;j<=n;j++) {
memset(dp[o^1],0,sizeof(dp[o^1]));
for(re int s=0;s<=len;++s)
for(re int k=0;k<=nS;++k) {
if(!dp[o][s][k]) continue;
upd(dp[o^1][s&(len^(1<<(j-1)))][k],dp[o][s][k]);
if(ma[j][i]=='*') {
int det=0;
if(i>1&&!(s>>(j-1)&1)) det++;
if(j>1&&!(s>>(j-2)&1)) det++;
if(j<n) ++det;if(i<m) ++det;
upd(dp[o^1][s|(1<<(j-1))][k+det],dqm(mod-dp[o][s][k]));
if(k+det>nS) nS=k+det;
}
}
o^=1;
}
int ans=0;
for(re int s=0;s<=len;++s)
for(re int k=0;k<=S;++k) upd(ans,1ll*dp[o][s][k]*inv[k]%mod);
printf("%d\n",1ll*ans*S%mod);return 0;
}