import java.awt.event.*;
import java.awt.*;

/**The basic object here if F[][], the list of flowers.
   This comes from EnhancedPolygon.flower[][].  Also,
   we keep track of the number of triangles, N*/


public class TreeSearch {

    public static int[] solution(int k) {
	int[][] s=solution();
	return s[k];
    }

    public static int[][] solution() {
	int[][] s={{0,0,0,0,0,0},{1,1,1,1,1,1}, //0,1
		   {0,0,0,1,1,1},{0,0,1,1,1,0},{0,1,1,1,0,0},{1,1,1,0,0,0},{1,1,0,0,0,1},{1,0,0,0,1,1}, //2-7
		   {1,1,0,1,0,0},{0,1,1,0,1,0},{0,0,1,1,0,1},{1,0,0,1,1,0},{0,1,0,0,1,1},{1,0,1,0,0,1}, //8-13
		   {1,1,0,0,1,0},{0,1,1,0,0,1},{1,0,1,1,0,0},{0,1,0,1,1,0},{0,0,1,0,1,1},{1,0,0,1,0,1}, //14-19
		   {1,0,1,0,1,0},{0,1,0,1,0,1},  //20,21
		   {0,0,0,0,1},{0,0,0,1,0},{0,0,1,0,0},{0,1,0,0,0},{1,0,0,0,0}, //22-27
		   {1,1,1,1,0},{1,1,1,0,1},{1,1,0,1,1},{1,0,1,1,1},{0,1,1,1,1}, //27-31
		   {1,1,0,0},{0,0,1,1},{0,1,1,0},{1,0,0,1},  //32-35
		   {1,0,1,0},{0,1,0,1}, //36,37
		   {0,0,0},{1,1,1}, //38,39
		   {0,1},{1,0}}; //40,41
	return s;
    }
    

    public static int recognizeLocal(int[] a) {
	for(int i=0;i<42;++i) {
	    if(ListHelp.matchOrdered(a,solution(i))==true) return i;
	}
	return -1;
    }


    public static boolean isComplete(int[] a) {
	boolean test=ListHelp.onList(-1,a);
	if(test==false) return true;
	return false;
    }

	
    /**Here S is the proposed solution: flower list, number of triangles, solution.
       A return of 0 means that it is inconsistent.  
       A return of 1 means that it is consistent.
       A return of 2 means that it is consistent and complete*/
    

    public static int isGood(int[][] F,int N,int[] S,int[] blocked) {
	if(ListHelp.onList(99,S)==true) return 0;
	int n=S.length;
	int[] T=new int[N];
	for(int i=0;i<N;++i) T[i]=-1;
	for(int i=n-1;i>=0;--i) {
	    int[] s=solution(S[i]);
	    int l=F[i].length;

	    if(s.length!=l) return 0;

	    for(int j=0;j<l;++j) {
		if(T[F[i][j]]==-1) T[F[i][j]]=s[j];
		else {
		    if(T[F[i][j]]!=s[j]) return 0;
		}
	    }
	}




	
       	int[][] SOL=solution();
	
	boolean complete=true;
	for(int i=0;i<F.length;++i) {
	    int[] g=assign(T,F[i]);
	    boolean def=isComplete(g);
	    int pos=ListHelp.position(g,SOL);
	    if((def==true)&&(pos==-1)) return 0;
	    if(ListHelp.onList(pos,blocked)==true) return 0;
	    if(def==false) complete=false;
	}
	
	if(complete==false) return 1;
	return 2;
    }




    


    /**assumes that we have a good assignment*/
    
    public static int[] assignVariables(int[][] F,int N,int[] S) {
	int n=S.length;
	int[] T=new int[N];
	for(int i=0;i<N;++i) T[i]=-1;
	for(int i=n-1;i>=0;--i) {
	    int[] s=solution(S[i]);
	    int l=F[i].length;
  	    for(int j=0;j<l;++j) T[F[i][j]]=s[j];
	}
	return T;
    }

    public static int[] assign(int[] T,int[] f) {
	int[] g=new int[f.length];
	for(int i=0;i<f.length;++i) g[i]=T[f[i]];
	return g;
    }






    public static boolean oppositeColor(int[] T,int h,int[] list) {
	if(T[h]==-1) return false;
	for(int i=0;i<3;++i) {
	    if(T[list[i]]==-1) return false;
	    if(T[list[i]]==T[h]) return false;
	}
	return true;
    }

}


