{$A+,B-,D+,E-,F-,G-,I+,L+,N+,O-,P-,Q-,R-,S-,T-,V-,X+}
{$M 65520,0,655360}
Program Block;
Const
  InFile='block.in';
  OutFile='block.out';
  TypeFile='types.in';
  MaxV=50;
  MaxNC=4;
  NBlocks=12;
  MaxTotal=107;
  TypeSeq:Array[1..NBlocks]Of Byte=(6,5,7,8,9,10,11,12,4,3,2,1);
Type
  TCube=Record X,Y,Z:ShortInt; End;
  TBlock=Record
    NC:Byte;
    C:Array[1..MaxNC]Of TCube;
    ID:Byte;
  End;
  TFigure=Record
    NC:Byte;
    C:Array[1..MaxV]Of TCube;
  End;
  TSeq=Array[1..MaxV]Of Byte;
Var
  B:Array[1..MaxTotal]Of TBlock;
  N:Byte;
  F:TFigure;
  MinFound:LongInt;
  CSeq,BSeq:TSeq;
  Used:Array[-6..12,-6..12,-6..12]Of Boolean;
  Timer:LongInt Absolute $40:$6C;
  EndTime:LongInt;
Procedure Load;
Var
  I,J,A:Byte;
  MX,MY,MZ:LongInt;
Begin
  Assign(Input,InFile);
  ReSet(Input);
  Read(F.NC);
  MX:=MaxLongInt;
  MY:=MaxLongInt;
  MZ:=MaxLongInt;
  For I:=1 To F.NC Do
    If Not SeekEOF Then Begin
      Read(F.C[I].X,F.C[I].Y,F.C[I].Z);
      If MX>F.C[I].X Then MX:=F.C[I].X;
      If MY>F.C[I].Y Then MY:=F.C[I].Y;
      If MZ>F.C[I].Z Then MZ:=F.C[I].Z;
    End;
  For I:=1 To F.NC Do Begin
    Dec(F.C[I].X,MX);
    Dec(F.C[I].Y,MY);
    Dec(F.C[I].Z,MZ);
  End;
  Close(Input);
  Assign(Input,TypeFile);
  ReSet(Input);
  For J:=1 To NBlocks Do Begin
    If Not SeekEOF Then Read(A);
    If Not SeekEOF Then Read(B[A].NC);
    MX:=MaxLongInt;
    MY:=MaxLongInt;
    MZ:=MaxLongInt;
    B[A].ID:=A;
    For I:=1 To B[A].NC Do
      If Not SeekEOF Then Begin
        Read(B[A].C[I].X,B[A].C[I].Y,B[A].C[I].Z);
        If MX>B[A].C[I].X Then MX:=B[A].C[I].X;
        If MY>B[A].C[I].Y Then MY:=B[A].C[I].Y;
        If MZ>B[A].C[I].Z Then MZ:=B[A].C[I].Z;
      End;
    For I:=1 To B[A].NC Do Begin
      Dec(B[A].C[I].X,MX);
      Dec(B[A].C[I].Y,MY);
      Dec(B[A].C[I].Z,MZ);
    End;
  End;
  Close(Input);
End;
Procedure GenerateAll;
Var
  I,J,K,L:Byte;
  B:TBlock;
Procedure NormalizeBlock(Var B:TBlock);
Var
  MX,MY,MZ:LongInt;
  I:Byte;
Begin
  MX:=MaxLongInt;
  MY:=MaxLongInt;
  MZ:=MaxLongInt;
  For I:=1 To B.NC Do Begin
    If MX>B.C[I].X Then MX:=B.C[I].X;
    If MY>B.C[I].Y Then MY:=B.C[I].Y;
    If MZ>B.C[I].Z Then MZ:=B.C[I].Z;
  End;
  For I:=1 To B.NC Do Begin
    Dec(B.C[I].X,MX);
    Dec(B.C[I].Y,MY);
    Dec(B.C[I].Z,MZ);
  End;
End;
Procedure RotateBlockX(Var B:TBlock);
Var
  I:Byte;
  T:LongInt;
Begin
  For I:=1 To B.NC Do Begin
    T:=B.C[I].Y;
    B.C[I].Y:=B.C[I].Z;
    B.C[I].Z:=-T;
  End;
End;
Procedure RotateBlockY(Var B:TBlock);
Var
  I:Byte;
  T:LongInt;
Begin
  For I:=1 To B.NC Do Begin
    T:=B.C[I].X;
    B.C[I].X:=B.C[I].Z;
    B.C[I].Z:=-T;
  End;
End;
Procedure RotateBlockZ(Var B:TBlock);
Var
  I:Byte;
  T:LongInt;
Begin
  For I:=1 To B.NC Do Begin
    T:=B.C[I].X;
    B.C[I].X:=B.C[I].Y;
    B.C[I].Y:=-T;
  End;
End;
Function Equal(Const A,B:TBlock):Boolean;
Var
  I,J:Byte;
  Ok:Boolean;
Begin
  Equal:=False;
  If A.NC<>B.NC Then Exit;
  For I:=1 To A.NC Do Begin
    Ok:=True;
    For J:=1 To B.NC Do If (A.C[I].X=B.C[J].X) And (A.C[I].Y=B.C[J].Y) And (A.C[I].Z=B.C[J].Z) Then Ok:=False;
    If Ok Then Exit;
  End;
  Equal:=True;
End;
Function Is(Const B:TBlock):Boolean;
Var
  I:Word;
Begin
  Is:=True;
  For I:=1 To N Do If Equal(Block.B[I],B) Then Exit;
  Is:=False;
End;
Procedure Add(Const B:TBlock);
Begin
  Inc(N);
  Block.B[N]:=B;
End;
Begin
  N:=NBlocks;
  For I:=1 To NBlocks Do Begin
    B:=Block.B[I];
    For J:=0 To 3 Do Begin
      For K:=0 To 3 Do Begin
        For L:=0 To 3 Do Begin
          NormalizeBlock(B);
          If Not Is(B) Then Add(B);
          RotateBlockZ(B);
        End;
        RotateBlockY(B);
      End;
      RotateBlockX(B);
    End;
  End;
End;
Procedure Run;
Var
  I:Word;
Procedure Next(Var X,Y,Z:LongInt);
Begin
  If X<6 Then Inc(X) Else Begin
    X:=0;
    If Y<6 Then Inc(Y) Else Begin
      Y:=0;
      Inc(Z);
    End;
  End;
End;
Procedure Rec(X,Y,Z:LongInt; CN:LongInt);
Var
  I,J,K,L:Byte;
  Ok:Boolean;
Begin
  If CN>=MinFound Then Exit;
  If Timer>=EndTime Then Exit;
  Next(X,Y,Z);
  While (Not Used[X,Y,Z]) And (Z<=6) Do Next(X,Y,Z);
  If Z>6 Then Begin
    MinFound:=CN;
    BSeq:=CSeq;
    Exit;
  End;
  For I:=1 To 12 Do
    For J:=1 To N Do If B[J].ID=TypeSeq[I] Then With B[J] Do Begin
      For K:=1 To NC Do Begin
        Ok:=True;
        For L:=1 To NC Do If (K<>L) Then
          If Not Used[X+C[L].X-C[K].X,Y+C[L].Y-C[K].Y,Z+C[L].Z-C[K].Z] Then Ok:=False;
        If Ok Then Begin
          For L:=1 To NC Do
            Used[X+C[L].X-C[K].X,Y+C[L].Y-C[K].Y,Z+C[L].Z-C[K].Z]:=False;
          CSeq[CN+1]:=J;
          Rec(X,Y,Z,CN+1);
          If Timer>=EndTime Then Exit;
          For L:=1 To NC Do
            Used[X+C[L].X-C[K].X,Y+C[L].Y-C[K].Y,Z+C[L].Z-C[K].Z]:=True;
        End;
      End;
    End;
End;
Begin
  MinFound:=MaxLongInt;
  FillChar(Used,SizeOf(Used),False);
  For I:=1 To F.NC Do Used[F.C[I].X,F.C[I].Y,F.C[I].Z]:=True;
  Rec(-1,0,0,0);
End;
Procedure Save;
Var
  I:LongInt;
Begin
  Assign(Output,OutFile);
  ReWrite(Output);
  WriteLn(MinFound);
  For I:=1 To MinFound-1 Do Write(B[BSeq[I]].ID,' ');
  WriteLn(B[BSeq[MinFound]].ID);
  Close(Output);
End;
Begin
  EndTime:=Timer+90;
  Load;
  GenerateAll;
  Run;
  Save;
End.