Problem:
博士の研究室

会津大学の鶴賀博士はとても研究熱心なことで有名です。彼の研究室には複数の学生がいますが、彼は毎日夜遅くまで研究をするので必ず最後に帰宅します。彼の研究室にはドアでつながった複数の部屋があり、最後に研究室を出る人がすべての部屋の明かりを消して帰宅することになっています。

最近、大学では省エネに力を入れているため、すべての明かりが消えているか厳しくチェックされます。困ったことに彼は誰もが認める極度の臆病者で、明かりの消えた部屋には決して入ることができません。そこで、彼はある部屋の照明のON/OFFを他の部屋から操作できるように研究室の照明設備を改造しました。

ところが、予算の都合で１つの部屋からコントロールできる部屋が限られています。その上、帰宅時の各部屋の明かりの状態も日によって異なるため、全ての明かりを消して出口までたどりつくのに毎日かなりの時間が掛かっています。そこで、研究員のあなたが博士を助けるためにプログラムを作成することになりました。

研究室の部屋情報、各部屋の明かりの点灯情報、各部屋の照明スイッチの情報を入力とし、博士がすべての明かりを消して帰宅できるかどうかを出力するプログラムを作成してください。ただし、部屋の数 n は 1 以上 15 以下の整数、ドアの数 m は 1 以上 30 以下の整数、照明の点灯情報 l は 0 または 1 の整数でそれぞれ消灯と点灯を表し、各部屋には 1 以上 n 以下の整数で番号が付与されているものとします。出口は番号 n の部屋に存在し、博士は常に部屋 1 からスタートするものとします。

なお、出力は、博士の取るべき行動に応じて以下の 3 通りに分けて出力します。

ケース１.
出口以外の全ての明かりを消して出口にたどりつける場合（経路の過程で出口を通ってもよい）。

You can go home in X steps.

と出力します。ここで X は部屋の移動、スイッチのON/OFF をそれぞれ１ステップとした場合の、博士の部屋から出口にたどり着くまでの最短のステップ数です。さらに、以下の文字列に従い博士の部屋から出口までの経路（博士のとるべき行動）を X 行で出力します。

部屋 R へ移動する場合

Move to room R.

部屋 R の照明を消す場合

Switch off room R.

部屋 R の照明を点灯する場合

Switch on room R.

ここで、R は部屋の番号を表します。博士がある部屋に移動した直後、複数のスイッチを操作して次の部屋に移動する場合は操作する部屋番号が小さいほうから出力してください。この条件を満たす限り、複数の解がある場合は、どれを出力してもかまいません。この情報をもとに、博士は無事帰宅することができます。

ケース2. 出口にたどり着くことはできるが、出口のある部屋以外の全ての明かりを消すことが
できない場合。

You can not switch off all lights.

と出力する。この場合、博士は省エネを守らなかったとして大学に罰せられます。

ケース3. どうあがいても出口にたどり着けない場合。

Help me!

と出力する。この場合、博士は警備員に緊急救助を求めます。

簡単な例を示します。この例では、研究室は 4 つの部屋で構成され、部屋 1 と 2、2 と 3、2 と 4 がそれぞれ繋がっています。また、部屋 1 及び 4 から部屋 2、3 の照明を操作することができ、部屋 3 から部屋 1、2、4 の照明を操作することができます。最初、部屋 2、3、4 の照明が消えた状態で、博士が部屋 1 にいます。

この状況では、博士が取るべき行動は次のようになります。

部屋2と3の照明をonにする。
部屋2に移動する。
部屋3に移動する。
部屋1の照明をoffにし、部屋4の照明をonにする。
部屋2に移動する。
部屋4に移動する。
部屋2と3の照明をoffにする。

これで博士は部屋 4 以外の照明を消すことができ、帰宅することができます。

Input

複数のデータセットの並びが入力として与えられます。入力の終わりはゼロ2つの行で示されます。
各データセットは以下の形式で与えられます。

n m
s1 t1
s2 t2
:
sm tm
l1 l2 ... ln
k1 r1 r2 ... rk1
k2 r1 r2 ... rk2
:
kn r1 r2 ... rkn

１行目に部屋の数 n (1 ≤ n ≤ 15) とドアの数 m (1 ≤ m ≤ 30) が空白区切りで与えられます。続く m 行に i 個目のドアの情報が与えられます。si ti は部屋 si と部屋 ti がドアで繋がっていることを表します。

続く１行に、部屋 i の照明の点灯情報 li (0 または 1) が空白区切りで与えられます。

続く n 行に部屋 i のスイッチ情報が与えられます。ki (0 ≤ ki ≤ 12) は部屋 i のスイッチの数、r1 ... rki は照明を操作できる部屋の番号を表します。

データセットの数は100 を超えません。

Output

データセットごとに、上記の 3 通りの結果に応じて以下の形式で出力します。

ケース 1 の場合

1行目: You can go home in X steps.

2行目: 1つ目の博士が取るべき行動

3行目: 2つ目の博士が取るべき行動

:

X+1 行目: X 個目の博士が取るべき行動

ケース 2 の場合

1 行目: You can not switch off all lights.

ケース 3 の場合

1 行目: Help me!

Sample Input

4 3
1 2
2 3
2 4
1 0 0 0
2 2 3
0
3 1 2 4
2 2 3
4 3
1 2
2 3
2 4
1 0 0 0
2 2 3
0
3 1 2 4
1 3
4 3
1 2
2 3
2 4
1 0 0 0
2 2 3
0
2 1 2
2 2 3
0 0

Output for the Sample Input

You can go home in 10 steps.
Switch on room 2.
Switch on room 3.
Move to room 2.
Move to room 3.
Switch off room 1.
Switch on room 4.
Move to room 2.
Move to room 4.
Switch off room 2.
Switch off room 3.
You can not switch off all lights.
Help me!

Solution in C (judge verdict: Accepted)

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define ROOM_MAX 15
#define DOOR_MAX 30

/* akari no zyoutai * iru heya */
#define DIJKSTRA_MAX_NODE ((1<<ROOM_MAX)*ROOM_MAX+1)
/* switch kirikae + heya idou */
#define DIJKSTRA_MAX_EDGE (DIJKSTRA_MAX_NODE*(ROOM_MAX+DOOR_MAX+1))

#define DIJKSTRA_DUMMY_ID (DIJKSTRA_MAX_NODE-1)
#define BIG_VALUE 10000000

typedef struct {
	int from,to;
	int cost;
} dijkstra_edge_t;

typedef struct {
	int node;
	int from;
	int cost;
} dijkstra_node_t;

int dijkstra_edge_num;
dijkstra_edge_t dijkstra_edge[DIJKSTRA_MAX_EDGE];
int dijkstra_node_edge[DIJKSTRA_MAX_NODE][2];
int dijkstra_queue_num;
dijkstra_node_t dijkstra_queue[DIJKSTRA_MAX_EDGE+1];
int dijkstra_cost[DIJKSTRA_MAX_NODE];
int dijkstra_from[DIJKSTRA_MAX_NODE];
char dijkstra_visited[DIJKSTRA_MAX_NODE];
int dijkstra_route_num;
int dijkstra_route[DIJKSTRA_MAX_NODE];

int dijkstra_comp(const void* x,const void* y) {
	const dijkstra_edge_t* a=(const dijkstra_edge_t*)x;
	const dijkstra_edge_t* b=(const dijkstra_edge_t*)y;
	if((a->from)>(b->from))return 1;
	if((a->from)<(b->from))return -1;
	if((a->to)>(b->to))return 1;
	if((a->to)<(b->to))return -1;
	return 0;
}

void dijkstra_queue_adjust(int pos) {
	int min=pos;
	if(pos*2+1<dijkstra_queue_num &&
		dijkstra_queue[min].cost>dijkstra_queue[pos*2+1].cost)
			min=pos*2+1;
	if(pos*2+2<dijkstra_queue_num &&
		dijkstra_queue[min].cost>dijkstra_queue[pos*2+2].cost)
			min=pos*2+2;
	if(min!=pos) {
		dijkstra_node_t temp;
		temp=dijkstra_queue[min];
		dijkstra_queue[min]=dijkstra_queue[pos];
		dijkstra_queue[pos]=temp;
		dijkstra_queue_adjust(min);
	} else if(pos>0)dijkstra_queue_adjust((pos-1)/2);
}

void dijkstra_queue_push(int node,int cost,int from) {
	dijkstra_node_t topush;
	topush.node=node;topush.cost=cost;topush.from=from;
	dijkstra_queue[dijkstra_queue_num++]=topush;
	dijkstra_queue_adjust(dijkstra_queue_num-1);
}

dijkstra_node_t dijkstra_queue_pop(void) {
	dijkstra_node_t result=dijkstra_queue[0];
	if(dijkstra_queue_num>0) {
		dijkstra_queue[0]=dijkstra_queue[--dijkstra_queue_num];
		dijkstra_queue_adjust(0);
	}
	return result;
}

void dijkstra_init(void) {
	dijkstra_edge_num=0;
}

void dijkstra_addedge(int from,int to,int cost) {
	dijkstra_edge[dijkstra_edge_num].from=from;
	dijkstra_edge[dijkstra_edge_num].to=to;
	dijkstra_edge[dijkstra_edge_num].cost=cost;
	dijkstra_edge_num++;
}

void dijkstra_setup(void) {
	int i;
	int prev;
	qsort(dijkstra_edge,dijkstra_edge_num,
		sizeof(dijkstra_edge_t),dijkstra_comp);
	prev=0;
	memset(dijkstra_node_edge,0,sizeof(dijkstra_node_edge));
	dijkstra_node_edge[0][0]=0;
	for(i=0;i<dijkstra_edge_num;i++) {
		if(dijkstra_edge[i].from!=dijkstra_edge[prev].from) {
			dijkstra_node_edge[dijkstra_edge[prev].from][1]=i;
			dijkstra_node_edge[dijkstra_edge[i].from][0]=i;
			prev=i;
		}
	}
	dijkstra_node_edge[dijkstra_edge[prev].from][1]=i;
}

int dijkstra_search(int from,int to) {
	int i,now,offset;
	memset(dijkstra_cost,0xFF,sizeof(dijkstra_cost));
	memset(dijkstra_visited,0,sizeof(dijkstra_visited));
	dijkstra_queue_num=0;
	dijkstra_queue_push(from,0,-1);
	while(dijkstra_queue_num>0) {
		dijkstra_node_t nownode=dijkstra_queue_pop();
		if(!dijkstra_visited[nownode.node]) {
			dijkstra_visited[nownode.node]=1;
			dijkstra_cost[nownode.node]=nownode.cost;
			dijkstra_from[nownode.node]=nownode.from;
			for(i=dijkstra_node_edge[nownode.node][0];
					i<dijkstra_node_edge[nownode.node][1];i++) {
				if(!dijkstra_visited[dijkstra_edge[i].to] &&
						(dijkstra_cost[dijkstra_edge[i].to]<0 ||
						dijkstra_cost[dijkstra_edge[i].to]>nownode.cost+dijkstra_edge[i].cost)) {
					dijkstra_queue_push(
						dijkstra_edge[i].to,
						nownode.cost+dijkstra_edge[i].cost,
						nownode.node
					);
					dijkstra_cost[dijkstra_edge[i].to]=nownode.cost+dijkstra_edge[i].cost;
				}
			}
		}
	}
	if(dijkstra_cost[to]>=0) {
		dijkstra_route_num=0;
		for(now=to,i=DIJKSTRA_MAX_NODE-1;now!=from && i>=0;i--) {
			dijkstra_route[i]=now;
			now=dijkstra_from[now];
			dijkstra_route_num++;
		}
		dijkstra_route[i]=from;
		dijkstra_route_num++;
		offset=i;
		for(i=0;i<dijkstra_route_num;i++) {
			dijkstra_route[i]=dijkstra_route[i+offset];
		}
	} else {
		dijkstra_route_num=0;
	}
	return dijkstra_cost[to];
}

int absint(int a) {
	return a<0?-a:a;
}

int get_id(int status,int room) {
	return status*ROOM_MAX+room;
}

int get_status(int id) {
	return id/ROOM_MAX;
}

int get_room(int id) {
	return id%ROOM_MAX;
}

void sort_and_print_switch(int sw[], int sw_num) {
	int i,j;
	for(i=sw_num-1;i>0;i--) {
		for(j=0;j<i;j++) {
			if(absint(sw[j])>absint(sw[j+1])) {
				int temp=sw[j];
				sw[j]=sw[j+1];
				sw[j+1]=temp;
			}
		}
	}
	for(i=0;i<sw_num;i++) {
		printf("Switch o%s room %d.\n",sw[i]<0?"ff":"n",absint(sw[i]));
	}
}

int main(void) {
	int n,m;
	while(scanf("%d%d",&n,&m)==2 && (n|m)!=0) {
		int i,j,k;
		int initial_status;
		int min_step;
		dijkstra_init();
		/* door wo yomikomu */
		for(i=0;i<m;i++) {
			int s,t;
			if(scanf("%d%d",&s,&t)!=2)return 1;
			s--;t--;
			for(j=0;j<(1<<n);j++) {
				/* kurai heya niwa hairenai */
				if((j&(1<<t))!=0) {
					dijkstra_addedge(get_id(j,s),get_id(j,t),1);
				}
				if((j&(1<<s))!=0) {
					dijkstra_addedge(get_id(j,t),get_id(j,s),1);
				}
			}
		}
		/* syoumei no zyouhou wo yomikomu */
		initial_status=0;
		for(i=0;i<n;i++) {
			int light;
			if(scanf("%d",&light)!=1)return 1;
			if(light!=0)initial_status|=(1<<i);
		}
		/* switch no zyouhou wo yomikomu */
		for(i=0;i<n;i++) {
			int snum;
			if(scanf("%d",&snum)!=1)return 1;
			for(j=0;j<snum;j++) {
				int r;
				if(scanf("%d",&r)!=1)return 1;
				r--;
				for(k=0;k<(1<<n);k++) {
					if(((k^(1<<r))&(1<<i))!=0) {
						dijkstra_addedge(get_id(k,i),get_id(k^(1<<r),i),1);
					}
				}
			}
		}
		/* akari wo subete kesenai kedo kaereru */
		for(i=0;i<(1<<n);i++) {
			dijkstra_addedge(get_id(i,n-1),DIJKSTRA_DUMMY_ID,0);
		}
		dijkstra_addedge(DIJKSTRA_DUMMY_ID,get_id(1<<(n-1),n-1),BIG_VALUE);
		dijkstra_setup();
		min_step=dijkstra_search(get_id(initial_status,0),get_id(1<<(n-1),n-1));
		if(min_step<0) {
			puts("Help me!");
		} else if(min_step<BIG_VALUE) {
			int switch_buffer[ROOM_MAX];
			int switch_num=0;
			printf("You can go home in %d steps.\n",min_step);
			for(i=1;i<dijkstra_route_num;i++) {
				if(get_room(dijkstra_route[i-1])!=get_room(dijkstra_route[i])) {
					/* heya wo idou sita */
					sort_and_print_switch(switch_buffer,switch_num);
					switch_num=0;
					printf("Move to room %d.\n",get_room(dijkstra_route[i])+1);
				} else {
					/* switch wo kirkiaeta */
					int status_from=get_status(dijkstra_route[i-1]);
					int status_to=get_status(dijkstra_route[i]);
					for(j=0;j<n;j++) {
						if((status_from&(1<<j))!=(status_to&(1<<j))) {
							if((status_to&(1<<j))!=0) {
								/* switch on */
								switch_buffer[switch_num++]=(j+1);
							} else {
								/* switch off */
								switch_buffer[switch_num++]=-(j+1);
							}
						}
					}
				}
			}
			sort_and_print_switch(switch_buffer,switch_num);
		} else {
			puts("You can not switch off all lights.");
		}
	}
	return 0;
}