#pragma GCC target("sse", "sse2", "sse3", "ssse3", "sse4")
#ifdef __APPLE__
# include <iostream>
# include <cmath>
# include <algorithm>
# include <stdio.h>
# include <cstdint>
# include <cstring>
# include <string>
# include <cstdlib>
# include <vector>
# include <bitset>
# include <map>
# include <queue>
# include <ctime>
# include <stack>
# include <set>
# include <list>
# include <random>
# include <deque>
# include <functional>
# include <iomanip>
# include <sstream>
# include <fstream>
# include <complex>
# include <numeric>
# include <immintrin.h>
# include <cassert>
# include <array>
# include <tuple>
# include <unordered_map>
# include <unordered_set>
# include <thread>
#else
# include <bits/stdc++.h>
#endif
#define F first
#define S second
#define MP make_pair
#define PB push_back
#define all(a) a.begin(),a.end()
#define len(a) (int)(a.size())
#define mp make_pair
#define pb push_back
#define fir first
#define sec second
using namespace std;
typedef pair<int, int> pii;
typedef long long ll;
typedef long double ld;
#if __APPLE__
#define D for (bool _FLAG = true; _FLAG; _FLAG = false)
#define LOG(...) print(#__VA_ARGS__" ::", __VA_ARGS__) << endl
template <class ...Ts> auto &print(Ts ...ts) { return ((cerr << ts << " "), ...); }
#else
#define D while (false)
#define LOG(...)
#endif
const int max_n = 1e5, inf = 1000111222;
const int md = 998244353;
namespace fastio {
const int buf_size = 1 << 14, small = 30;
char buf_read[buf_size + small];
char buf_write[buf_size + small];
char *ptr_read = buf_read + buf_size;
char *ptr_write = buf_write;
long long read_int() {
auto getChar = []() {
if (ptr_read == buf_read + buf_size){
buf_read[fread(buf_read, 1, buf_size, stdin)] = 0;
ptr_read = buf_read;
}
return *ptr_read++;
};
char c = getChar();
while (c && (c < '0' || c > '9') && c != '-') {
c = getChar();
}
long long z = 1;
if (c == '-') {
z = -1;
c = getChar();
}
long long res = 0;
while (c >= '0' && c <= '9'){
res = res * 10 + (c - '0');
c = getChar();
}
return z * res;
}
void write_flush() {
fwrite(buf_write, 1, ptr_write - buf_write, stdout);
ptr_write = buf_write;
}
void write_int(long long x) {
if (x < 0) {
*ptr_write++ = '-';
x = -x;
}
char *start = ptr_write;
if (!x) {
*ptr_write++ = '0';
}
while (x) {
*ptr_write++ = x % 10 + '0';
x /= 10;
}
reverse(start, ptr_write);
if (ptr_write >= buf_write + buf_size) {
write_flush();
}
}
void write_char(char c) {
*ptr_write++ = c;
if (ptr_write >= buf_write + buf_size) {
write_flush();
}
}
}
template<typename Edge>
class GraphIterator {
public:
class OutgoingEdges {
public:
OutgoingEdges(const GraphIterator *g, int l, int r): g(g), l(l), r(r) {
}
const Edge* begin() const {
if (l == r) {
return 0;
}
return &g->prepared_edges[l];
}
const Edge* end() const {
if (l == r) {
return 0;
}
return &g->prepared_edges[r];
}
private:
int l, r;
const GraphIterator *g;
};
void clear() {
prepared_edges.clear();
edges.clear();
start.clear();
prepared = false;
}
void add_edge(int from, const Edge &e) {
assert(!prepared && from >= 0);
edges.push_back({from, e});
}
void prepare() {
assert(!prepared);
int n = 0;
for (const auto &e : edges) {
n = max(n, e.first);
}
n += 2;
start.resize(n);
for (const auto &e : edges) {
++start[e.first + 1];
}
for (int i = 1; i < n; ++i) {
start[i] += start[i - 1];
}
prepared_edges.resize(edges.size() + 1);
auto counter = start;
for (const auto &e : edges) {
prepared_edges[counter[e.first]++] = e.second;
}
prepared = true;
}
OutgoingEdges operator [] (int from) const {
assert(prepared);
if (from < 0 || from + 1 >= start.size()) {
return {this, 0, 0};
}
return {this, start[from], start[from + 1]};
}
private:
vector<Edge> prepared_edges;
vector<pair<int, Edge>> edges;
vector<int> start;
bool prepared = false;
};
GraphIterator<int> reb;
int x[max_n];
int sz[max_n];
int main() {
// freopen("input.txt", "r", stdin);
// freopen("output.txt", "w", stdout);
ios_base::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
int n,m;
n=fastio::read_int();
m=fastio::read_int();
for (int i=0;i<n;i++){
x[i]=fastio::read_int();
}
vector<pii> edges(m);
for (int i=0;i<m;i++){
int u=fastio::read_int();
int v=fastio::read_int();
if (u>v){
swap(u,v);
}
edges[i]=mp(u,v);
sz[u]++;
sz[v]++;
}
for (auto& e:edges){
int u=e.fir;
int v=e.sec;
if (sz[u]>sz[v]){
swap( u,v);
}
reb.add_edge(u,v);
}
reb.prepare();
int ans=0;
memset(sz,0,sizeof(sz));
for (int i=0;i<n;i++){
for (auto j:reb[i]){
sz[j]=x[j];
}
for (auto j:reb[i]){
long long sum=0;
for (auto k:reb[j]){
sum+=sz[k];
}
ans+=1ll*x[i]*x[j]%md*(sum%md)%md;
if (ans>=md){
ans-=md;
}
}
for (auto j:reb[i]){
sz[j]=0;
}
}
cout<<ans<<"\n";
}