#include <bits/stdc++.h>
using namespace std;
typedef bool boolean;

#define ll long long

void exgcd(int a, int b, int& x, int& y) {
	if (!b) {
		x = 1, y = 0;
	} else {
		exgcd(b, a % b, y, x);
		y -= (a / b) * x;
	}
}

int inv(int a, int n) {
	int x, y;
	exgcd(a, n, x, y);
	return (x < 0) ? (x + n) : (x);
}

const int Mod = 998244353;

template <const int Mod = :: Mod>
class Z {
	public:
		int v;

		Z() : v(0) {	}
		Z(int x) : v(x){	}
		Z(ll x) : v(x % Mod) {	}

		friend Z operator + (const Z& a, const Z& b) {
			int x;
			return Z(((x = a.v + b.v) >= Mod) ? (x - Mod) : (x));
		}
		friend Z operator - (const Z& a, const Z& b) {
			int x;
			return Z(((x = a.v - b.v) < 0) ? (x + Mod) : (x));
		}
		friend Z operator * (const Z& a, const Z& b) {
			return Z(a.v * 1ll * b.v);
		}
		friend Z operator ~(const Z& a) {
			return inv(a.v, Mod);
		}
		friend Z operator - (const Z& a) {
			return Z(0) - a;
		}
		Z& operator += (Z b) {
			return *this = *this + b;
		}
		Z& operator -= (Z b) {
			return *this = *this - b;
		}
		Z& operator *= (Z b) {
			return *this = *this * b;
		}
		friend boolean operator == (const Z& a, const Z& b) {
			return a.v == b.v;
		} 
};

Z<> qpow(Z<> a, int p) {
	Z<> rt = Z<>(1), pa = a;
	for ( ; p; p >>= 1, pa = pa * pa) {
		if (p & 1) {
			rt = rt * pa;
		}
	}
	return rt;
}

typedef Z<> Zi;

const int N = 805;

int m, n;
int h[N];
Zi pw2[N * N];
Zi f[N][N][2];
Zi comb[N][N];
int L[N], R[N];

void prepare(int n) {
	comb[0][0] = 1;
	for (int i = 1; i <= n; i++) {
		comb[i][0] = comb[i][i] = 1;
		for (int j = 1; j < i; j++) {
			comb[i][j] = comb[i - 1][j] + comb[i - 1][j - 1];
		}
	}
	pw2[0] = 1;
	for (int i = 1; i <= n * n + 3; i++) {
		pw2[i] = pw2[i - 1] + pw2[i - 1];
	}
}

int build(int l, int r, int bh) {
	static Zi g[N][2];
	int p = ++n;
	L[p] = l, R[p] = r;
	int mi = h[l];
	for (int i = l; i <= r; i++) {
		mi = min(mi, h[i]);
	}
	int ls = l - 1;
	vector<int> son;
	int cnew = 0;
	for (int i = l; i <= r; i++) {
		if (h[i] == mi) {
			if (i - 1 >= ls + 1)
				son.push_back(build(ls + 1, i - 1, mi));
			ls = i, cnew++;
		}
	}
	if (ls < r)
		son.push_back(build(ls + 1, r, mi));
	for (int i = 0; i <= cnew; i++)
		f[p][i][i == 0] = comb[cnew][i];
	int lenp = cnew;
	for (auto e : son) {
		int lene = R[e] - L[e] + 1;
		for (int i = 0; i <= lenp + lene; i++)
			g[i][0] = g[i][1] = 0;
		for (int i = 0; i <= lenp; i++) {
			for (int j = 0; j <= lene; j++) {
				g[i + j][0] += f[p][i][0] * f[e][j][0];
				g[i + j][1] += f[p][i][1] * f[e][j][1];
			}
		}
		for (int i = 1; i <= lenp; i++) {
			g[i][0] += f[p][i][0] * f[e][0][1];
		}
		for (int i = 1; i <= lene; i++) {
			g[i][0] += f[e][i][0] * f[p][0][1];
		}
		lenp += lene;
		for (int i = 0; i <= lenp; i++)
			f[p][i][0] = g[i][0], f[p][i][1] = g[i][1];
	}
	int hei = mi - bh, len = r - l + 1;
	for (int t = 1; t <= hei; t++) {
		f[p][0][1] *= pw2[len];
		for (int i = 1; i <= len; i++) {
			Zi coef = (i & 1) ? (Mod - 1) : 1; 
			f[p][i][1] = (f[p][i][1] * (pw2[len - i] - 1) + f[p][i][0] * coef);
			f[p][i][0] *= pw2[len - i];
		}
	}
/*	cerr << p << " [" << l << ", " << r << "]:\n";
	for (int i = 0; i <= len; i++)
		cerr << f[p][i][0].v << " ";
	cerr << '\n';
	for (int i = 0; i <= len; i++)
		cerr << f[p][i][1].v << " ";
	cerr << '\n'; */
	return p;
}

int main() {
	scanf("%d", &m);
	for (int i = 1; i <= m; i++) {
		scanf("%d", h + i);
	}
	prepare(m);
	build(1, m, 0);
	Zi ans = 0;
	for (int i = 0; i <= m; i++)
		ans += f[1][i][1];
	printf("%d\n", ans.v);
	return 0;
}


Measured memory_bytes: 10496