#include<iostream>
#include<stack>
#include<queue>
#include<cstring>
#include<cstdio>
using namespace std;
typedef long long ll;
typedef pair<int,int> PI;
const int inf=0x3f;
const int maxn=1111;
struct Node
{
int v,next,val;
} edge[maxn];
int head[maxn],tot,dis[maxn],n,m;
int pre[maxn]; //松弛数组
bool vis[maxn]; //标记
priority_queue<PI> Q; //大根堆优化
void add(int a,int b,int c)
{
edge[++tot].v=b;
edge[tot].val=c;
edge[tot].next=head[a];
head[a]=tot;
}
void init()//多组输入调用
{
tot=0;
memset(head,0,sizeof(head));
}
void dijkstra(int s)
{
memset(dis,inf,sizeof(dis));
memset(vis,0,sizeof(vis));
memset(pre,-1,sizeof(pre));
while(Q.size())
Q.pop();
dis[s] = 0;
Q.push(make_pair(0,s));
while(!Q.empty())
{
int x=Q.top().second;
Q.pop();
if(vis[x])
continue;
vis[x]=1;
for(int i=head[x];i;i=edge[i].next)
{
int y=edge[i].v;
if(dis[x]+edge[i].v<dis[y])
{
dis[y]=dis[x]+edge[i].val;
if(!vis[y])
Q.push(make_pair(-dis[y],y));
pre[y]=x;
}
}
}
}
int main()
{
int s,e;
init();
while(cin>>n>>m>>s>>e)
{
init();
while(m--)
{
int x,y,z;
cin>>x>>y>>z;
add(x,y,z);
}
dijkstra(s);
if(dis[e]>inf)
{
cout<<"no answer"<<endl;
return 0;
}
cout<<dis[e]<<endl;
stack<int> ss;
for(int i=e;~i;i=pre[i])
{
ss.push(i);
}
while(ss.size())
{
cout<<'v';
cout<<ss.top()<<" ";
ss.pop();
}
cout<<endl;
}
}
//注意inf在有的服务器上不能开的太大,容易wa