#include<iostream>
using namespace std;
#define MAX 0x7fffffff
struct Esave
{
long int save;
long int LastIndex;
};
struct Mlist
{
int to;
long int cost;
long int FrontIndex;
};
long int Gmap(Esave *nl, Mlist *me, long int i, int c1, int c2, long int ct)
{
me[i].cost = ct;
me[i].to = c2;
me[i].FrontIndex = nl[c1].LastIndex;
nl[c1].LastIndex = i++;
me[i].cost = ct;
me[i].to = c1;
me[i].FrontIndex = nl[c2].LastIndex;
nl[c2].LastIndex = i++;
return i;
}
void EMDFS(Esave*nl, Mlist*me, long int *min, int c1, int c2,
bool *visit, long int*max, long int lastmin, long int *count, long int maxx)
{
long int t, tempmax, tempmin, id;
visit[c1] = false;
t = nl[c1].LastIndex;
tempmin = lastmin;
tempmax = maxx;
while (t>0)
{
id = me[t].to;
tempmin = lastmin + me[t].cost;
tempmax = maxx + nl[id].save;
if (visit[id] == true && id != c2)
EMDFS(nl, me, min, id, c2, visit, max, tempmin, count, tempmax);
else if (id == c2)
{
if ((*min)>tempmin)
{
(*min) = tempmin;
(*max) = tempmax;
(*count)=1;
}
else if ((*min) == tempmin)
{
if ((*max)<tempmax)
{
(*max) = tempmax;
}
(*count)++;
}
}
t = me[t].FrontIndex;
}
visit[c1] = true;
}
int main()
{
int N, i, link1, link2, C1, C2;
long int M, costt, temp, t;
bool *flag;
Esave *NLastIndex;
Mlist *MEmergency;
cin >> N >> M >> C1 >> C2;
NLastIndex = new Esave[N];
MEmergency = new Mlist[(M + 1) * 2];
MEmergency[0].cost = 0;
MEmergency[0].to = 0;
MEmergency[0].FrontIndex = 0;
flag = new bool[N];
for (i = 0; i<N; i++)
{
cin >> NLastIndex[i].save;
NLastIndex[i].LastIndex = 0;
flag[i] = true;
}
for (i = 0, temp = 1; i<M; i++)
{
cin >> link1 >> link2 >> costt;
temp = Gmap(NLastIndex, MEmergency, temp, link1, link2, costt);
}
costt = MAX;
temp = NLastIndex[C1].save;
t = 1;
EMDFS(NLastIndex, MEmergency, &costt, C1, C2, flag, &temp, MEmergency[C1].cost, &t, temp);
cout << t << " " << temp << endl;
delete []NLastIndex;
delete []MEmergency;
return 0;
}