Problem:
Score : 600 points

Problem Statement

We have a grid with A horizontal rows and B vertical columns, with the squares painted white. On this grid, we will repeatedly apply the following operation:

Assume that the grid currently has a horizontal rows and b vertical columns. Choose "vertical" or "horizontal".

If we choose "vertical", insert one row at the top of the grid, resulting in an (a+1) \times b grid.

If we choose "horizontal", insert one column at the right end of the grid, resulting in an a \times (b+1) grid.

Then, paint one of the added squares black, and the other squares white.

Assume the grid eventually has C horizontal rows and D vertical columns. Find the number of ways in which the squares can be painted in the end, modulo 998244353.

Constraints

1 \leq A \leq C \leq 3000

1 \leq B \leq D \leq 3000

A, B, C, and D are integers.

Input

Input is given from Standard Input in the following format:

A B C D

Output

Print the number of ways in which the squares can be painted in the end, modulo 998244353.

Sample Input 1

1 1 2 2

Sample Output 1

3

Any two of the three squares other than the bottom-left square can be painted black.

Sample Input 2

2 1 3 4

Sample Output 2

65

Sample Input 3

31 41 59 265

Sample Output 3

387222020

Solution in C++ (GCC 9.2.1) (judge verdict: Wrong Answer)

#include<cstdio>
#include<cmath>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
long long int fie[5000][5000];
int main(){

    long long int A,B,C,D;
    cin>>A>>B>>C>>D;
    /*
    fie[A][B][0]={1};
    for(int i=A;i<=C;i++){
        for(int j=B;j<=D;j++){
            for(int k=0;k<2;k++){
                //if(i==A&&j==B&&k==0)continue;
                if(k==0){
                    fie[i+1][j][1]+=fie[i][j][k]*j;
                    fie[i][j+1][0]+=fie[i][j][k]*(i-1);
                    fie[i][j+1][1]+=fie[i][j][k];
                }
                if(k==1){
                    fie[i+1][j][1]+=fie[i][j][k]*j;
                    fie[i][j+1][1]+=fie[i][j][k]*(i-1);
                    fie[i][j+1][2]+=fie[i][j][k];
                }
                if(k==0){
                    fie[i+1][j][1]+=fie[i][j][k]*j;
                    fie[i][j+1][2]+=fie[i][j][k]*(j-1);
                    fie[i][j+1][2]+=fie[i][j][k];
                }
            }
        }
    }
    cout<<fie[C][D][0]+fie[C][D][1]+fie[C][D][2]<<endl;
    */

    fie[A][B]=1;
    for(long long int i=A;i<=C;i++){
        for(long long int j=B;j<=D;j++){
            if(i==A&&j==B)continue;
            fie[i][j]=fie[i-1][j]*j+fie[i][j-1]*i-(i-1)*(j-1)*fie[i-1][j-1];
            //printf("fie[%d][%d]=[%lld]+[%lld]-[%d]=[%d]\n",i,j,fie[i-1][j]*j,fie[i][j-1]*i,(i-A)*(j-B),fie[i][j]);
            //printf("hoge");
            fie[i][j]=(fie[i][j]+(long long int)998244353*(long long int)10000)%(long long int)998244353;
        }
    }

    for(int i=0;i<5;i++){
        for(int j=0;j<5;j++){
            //printf("[%lld]",fie[i][j]);
        }
        //cout<<endl;
    }

    cout<<fie[C][D]<<endl;

    /*
    long long int ans=1;
    while(1){
        if(A<C&&B<D){
            ans*=A*B+A+B;
            A++;
            B++;
            ans%=998244353;
        }
        else if(A<C){
            A++;
            ans*=B;
            ans%=998244353;
        }
        else if(B<D){
            B++;
            ans*=A;
            ans%=998244353;
        }
        else{
            break;
        }
    }
    cout<<ans<<endl;
*/
    return 0;
}