Advertisement
Guest User

Rubiks Cube Solver

a guest
May 20th, 2011
1,552
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 45.16 KB | None | 0 0
  1. import random
  2.  
  3. class face(object):
  4.     struc = []
  5.     name = None
  6.     value = None
  7.  
  8.     def __init__(self, name, value, faces):
  9.         self.struc = []
  10.         self.name = name
  11.         self.value = value
  12.         self.FRONT, self.BACK, self.LEFT, self.RIGHT, self.UP, self.DOWN = faces
  13.         for x in xrange(3):
  14.             self.struc.append([])
  15.             for y in xrange(3):
  16.                 self.struc[x].append(value)
  17.        
  18.     def getName(self):
  19.         return self.name
  20.  
  21.     def num2coord(self, num):
  22.         return (num / 3, num % 3)
  23.  
  24.     def coord2num(self, coord):
  25.         row,col = coord
  26.         return row*3+col
  27.  
  28.     def getColumns(self, _2dlist=None):
  29.         if _2dlist == None:
  30.             _2dlist = self.struc
  31.         ret = []
  32.         for i in xrange(len(_2dlist[0])):
  33.             ret.append([])
  34.             for j in xrange(len(_2dlist)):
  35.                 ret[i].append(_2dlist[j][i])
  36.         return ret
  37.  
  38.     def getUpFacePos(self, frontFace, row, col):
  39.         if frontFace == self.FRONT or face == self.UP or frontFace == self.DOWN:
  40.             return (row, col)
  41.         elif frontFace == self.BACK:
  42.             return self.num2coord(8 - self.coord2num((row,col)))
  43.         elif frontFace == self.LEFT:
  44.             cmap = [2,5,8,1,4,7,0,3,6]
  45.             return self.num2coord(cmap[self.coord2num((row,col))])
  46.         elif frontFace == self.RIGHT:
  47.             cmap = [6,3,0,7,4,1,8,5,2]
  48.             return self.num2coord(cmap[self.coord2num((row,col))])
  49.        
  50.     def getDownFacePos(self, frontFace, row, col):
  51.         if frontFace == self.FRONT or frontFace == self.UP or frontFace == self.DOWN:
  52.             return (row, col)
  53.         elif frontFace == self.BACK:
  54.             return self.num2coord(8 - self.coord2num((row,col)))
  55.         elif frontFace == self.LEFT:
  56.             cmap = [6,3,0,7,4,1,8,5,2]
  57.             return self.num2coord(cmap[self.coord2num((row,col))])
  58.         elif frontFace == self.RIGHT:
  59.             cmap = [2,5,8,1,4,7,0,3,6]
  60.             return self.num2coord(cmap[self.coord2num((row,col))])
  61.  
  62.     def getPosFromUp(self, row, col):
  63.         if self.name == self.FRONT or self.name == self.UP or self.name == self.DOWN:
  64.             return (row, col)
  65.         elif self.name == self.BACK:
  66.             return self.num2coord(8 - self.coord2num((row,col)))
  67.         elif self.name == self.LEFT:
  68.             cmap = [6,3,0,7,4,1,8,5,2]
  69.             return self.num2coord(cmap[self.coord2num((row,col))])
  70.         elif self.name == self.RIGHT:
  71.             cmap = [2,5,8,1,4,7,0,3,6]
  72.             return self.num2coord(cmap[self.coord2num((row,col))])
  73.  
  74.     def getPosFromDown(self, row, col):
  75.         if self.name == self.FRONT or self.name == self.UP or self.name == self.DOWN:
  76.             return (row, col)
  77.         elif self.name == self.BACK:
  78.             return self.num2coord(8 - self.coord2num((row,col)))
  79.         elif self.name == self.LEFT:
  80.             cmap = [2,5,8,1,4,7,0,3,6]
  81.             return self.num2coord(cmap[self.coord2num((row,col))])
  82.         elif self.name == self.RIGHT:
  83.             cmap = [6,3,0,7,4,1,8,5,2]
  84.             return self.num2coord(cmap[self.coord2num((row,col))])
  85.  
  86.     def getCoords(self, key):
  87.         x, y = -1, -1
  88.         if len(key) == 2:
  89.             x,y = self.num2coord(key[1])
  90.             key = key[0], x, y
  91.         if key[0] == self.UP:
  92.             x,y = self.getPosFromUp(key[1], key[2])
  93.         elif key[0] == self.DOWN:
  94.             x,y = self.getPosFromDown(key[1], key[2])
  95.         elif self.name == self.UP:
  96.             x,y = self.getUpFacePos(*key)
  97.         elif self.name == self.DOWN:
  98.             x,y = self.getDownFacePos(*key)
  99.         else:
  100.             x,y = key[1], key[2]
  101.         return (x,y)
  102.  
  103.     def __eq__(self, other):
  104.         if type(other) == str:
  105.             return self.name == other
  106.         else:
  107.             return self.name == other.name
  108.  
  109.     def __getitem__(self, key):
  110.         x,y=self.getCoords(key)
  111.         return self.struc[x][y]
  112.    
  113.     def __setitem__(self, key, value):
  114.         x,y=self.getCoords(key)
  115.         self.struc[x][y] = value
  116.  
  117.     def __len__(self):
  118.         return 3
  119.  
  120.     def __str__(self):
  121.         return str(self.struc)
  122.  
  123.     def __repr__(self):
  124.         return str(self)
  125.  
  126.     def isSolved(self):
  127.         c = self.struc[0][0]
  128.         for x in self.struc:
  129.             for y in x:
  130.                 if c != y: return False
  131.         return True
  132.  
  133.     def listRep(self, frontFace):
  134.         r = []
  135.         for i in xrange(9):
  136.             r.append(self[frontFace, i])
  137.         return r
  138.  
  139.     def reOrder(self, frontFace, newOrder):
  140.         oldDat = self.listRep(frontFace)
  141.         for i in xrange(9):
  142.             self[frontFace, i] = oldDat[newOrder[i]]
  143.  
  144.     def copy(self):
  145.         r = face(self.name, self.value, (self.FRONT, self.BACK, self.LEFT, self.RIGHT, self.UP, self.DOWN))
  146.         r.struc = []
  147.         for x in xrange(3):
  148.             r.struc.append([])
  149.             for y in xrange(3):
  150.                 r.struc[x].append(self.struc[x][y])
  151.  
  152.         return r
  153.        
  154. class cube(object):
  155.     W, R, B, O, G, Y = 0, 1, 2, 3, 4, 5
  156.     colors = [W, Y, R, O, G, B] # F, B, L, R, U, D
  157.     colLet = {W:"W", R:"R", B:"B", O:"O", G:"G", Y:"Y"}
  158.     FRONT = "F"
  159.     BACK = "B"
  160.     LEFT = "L"
  161.     RIGHT = "R"
  162.     UP = "U"
  163.     DOWN = "D"
  164.  
  165.     cube = {}
  166.     moveList = []
  167.  
  168.     lastFace = -1
  169.     recording = False
  170.    
  171.     def __init__(self):
  172.         self.cube = {}
  173.         self.moveList = []
  174.         self.createCube()
  175.  
  176.     def copy(self):
  177.         r = cube()
  178.         faces = [self.FRONT, self.BACK, self.LEFT, self.RIGHT, self.UP, self.DOWN]
  179.         for i in xrange(len(self.colors)):
  180.             r.cube[faces[i]] = self.cube[faces[i]].copy()
  181.         return r
  182.  
  183.     def startRecord(self):
  184.         self.moveList = []
  185.         self.recording = True
  186.  
  187.     def endRecord(self):
  188.         self.recording = False
  189.        
  190.     def createCube(self):
  191.         faces = [self.FRONT, self.BACK, self.LEFT, self.RIGHT, self.UP, self.DOWN]
  192.         for i in xrange(len(self.colors)):
  193.             self.cube[faces[i]] = face(faces[i], self.colors[i], faces)          
  194.                    
  195.     def getColumns(self, frontFace, face):
  196.         ret = []
  197.         for i in xrange(len(face)):
  198.             ret.append([])
  199.             for j in xrange(len(face)):
  200.                 ret[i].append(face[(frontFace,j,i)])
  201.         return ret
  202.    
  203.     def getFaces(self, frontFace):
  204.         if frontFace == self.BACK:
  205.             return self.BACK, self.FRONT, self.RIGHT, self.LEFT, self.UP, self.DOWN
  206.         elif frontFace == self.LEFT:
  207.             return self.LEFT, self.RIGHT, self.BACK, self.FRONT, self.UP, self.DOWN
  208.         elif frontFace == self.RIGHT:
  209.             return self.RIGHT, self.LEFT, self.FRONT, self.BACK, self.UP, self.DOWN
  210.         elif frontFace == self.UP:
  211.             return self.UP, self.DOWN, self.LEFT, self.RIGHT, self.BACK, self.FRONT
  212.         elif frontFace == self.DOWN:
  213.             return self.DOWN, self.UP, self.LEFT, self.RIGHT, self.FRONT, self.BACK
  214.         else:
  215.             return self.FRONT, self.BACK, self.LEFT, self.RIGHT, self.UP, self.DOWN
  216.  
  217.     def inverseMove(self, move):
  218.         return move[0] if len(move)==2 else (move+"'")
  219.        
  220.     def turn(self, face, clockwise=True):
  221.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(face)
  222.         if self.recording:
  223.             g = "%s%s" % (face, "" if clockwise else "'")
  224.             self.moveList.append(g)
  225.             f = True
  226.             while f:
  227.                 f = False
  228.                 if len(self.moveList) > 1:
  229.                     if self.moveList[-1] == self.inverseMove(self.moveList[-2]):
  230.                         self.moveList.pop(); self.moveList.pop()
  231.                         f = True
  232.                 if len(self.moveList) > 2:
  233.                     if self.moveList[-1] == self.moveList[-2] == self.moveList[-3]:
  234.                         self.moveList.pop(); self.moveList.pop()
  235.                         self.moveList[-1] = self.inverseMove(self.moveList[-1])
  236.                         f = True
  237.         if clockwise:
  238.             lRep = self.cube[LEFT].listRep(FRONT)
  239.             rRep = self.cube[RIGHT].listRep(FRONT)
  240.             uRep = self.cube[UP].listRep(FRONT)
  241.             dRep = self.cube[DOWN].listRep(FRONT)
  242.  
  243.             #FRONT
  244.             self.cube[FRONT].reOrder(FRONT, [6,3,0,7,4,1,8,5,2])
  245.             #LEFT
  246.             self.cube[LEFT][FRONT, 2] = dRep[0]
  247.             self.cube[LEFT][FRONT, 5] = dRep[1]
  248.             self.cube[LEFT][FRONT, 8] = dRep[2]
  249.             #DOWN
  250.             self.cube[DOWN][FRONT, 0] = rRep[6]
  251.             self.cube[DOWN][FRONT, 1] = rRep[3]
  252.             self.cube[DOWN][FRONT, 2] = rRep[0]
  253.             #RIGHT
  254.             self.cube[RIGHT][FRONT, 0] = uRep[6]
  255.             self.cube[RIGHT][FRONT, 3] = uRep[7]
  256.             self.cube[RIGHT][FRONT, 6] = uRep[8]
  257.             #UP
  258.             self.cube[UP][FRONT, 6] = lRep[8]
  259.             self.cube[UP][FRONT, 7] = lRep[5]
  260.             self.cube[UP][FRONT, 8] = lRep[2]
  261.         else:
  262.             lRep = self.cube[LEFT].listRep(FRONT)
  263.             rRep = self.cube[RIGHT].listRep(FRONT)
  264.             uRep = self.cube[UP].listRep(FRONT)
  265.             dRep = self.cube[DOWN].listRep(FRONT)
  266.  
  267.             #FRONT
  268.             self.cube[FRONT].reOrder(FRONT, [2,5,8,1,4,7,0,3,6])
  269.             #LEFT
  270.             self.cube[LEFT][FRONT, 2] = uRep[8]
  271.             self.cube[LEFT][FRONT, 5] = uRep[7]
  272.             self.cube[LEFT][FRONT, 8] = uRep[6]
  273.             #DOWN
  274.             self.cube[DOWN][FRONT, 0] = lRep[2]
  275.             self.cube[DOWN][FRONT, 1] = lRep[5]
  276.             self.cube[DOWN][FRONT, 2] = lRep[8]
  277.             #RIGHT
  278.             self.cube[RIGHT][FRONT, 0] = dRep[2]
  279.             self.cube[RIGHT][FRONT, 3] = dRep[1]
  280.             self.cube[RIGHT][FRONT, 6] = dRep[0]
  281.             #UP
  282.             self.cube[UP][FRONT, 6] = rRep[0]
  283.             self.cube[UP][FRONT, 7] = rRep[3]
  284.             self.cube[UP][FRONT, 8] = rRep[6]
  285.            
  286.  
  287.     def turnMiddle(self, face):
  288.         if self.recording:
  289.             clockwise = face in (self.RIGHT, self.UP, self.BACK)
  290.             dic = {self.LEFT:"M",self.RIGHT:"M",
  291.                    self.UP:"E",self.DOWN:"E",
  292.                    self.FRONT:"S",self.BACK:"S"}
  293.             g = "%s%s" % (dic[face], "" if clockwise else "'")
  294.             self.moveList.append(g)
  295.             f = True
  296.             while f:
  297.                 f = False
  298.                 if len(self.moveList) > 1:
  299.                     if self.moveList[-1] == self.inverseMove(self.moveList[-2]):
  300.                         self.moveList.pop(); self.moveList.pop()
  301.                         f = True
  302.                 if len(self.moveList) > 2:
  303.                     if self.moveList[-1] == self.moveList[-2] == self.moveList[-3]:
  304.                         self.moveList.pop(); self.moveList.pop()
  305.                         self.moveList[-1] = self.inverseMove(self.moveList[-1])
  306.                         f = True
  307.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(face)
  308.         up = [self.cube[UP][(self.cube[FRONT], 3)], self.cube[UP][(self.cube[FRONT], 4)],
  309.               self.cube[UP][(self.cube[FRONT], 5)]]
  310.         left = [self.cube[LEFT][(self.cube[FRONT], 1)], self.cube[LEFT][(self.cube[FRONT], 4)],
  311.               self.cube[LEFT][(self.cube[FRONT], 7)]]
  312.         down = [self.cube[DOWN][(self.cube[FRONT], 3)], self.cube[DOWN][(self.cube[FRONT], 4)],
  313.               self.cube[DOWN][(self.cube[FRONT], 5)]]
  314.         right = [self.cube[RIGHT][(self.cube[FRONT], 1)], self.cube[RIGHT][(self.cube[FRONT], 4)],
  315.               self.cube[RIGHT][(self.cube[FRONT], 7)]]
  316.  
  317.         self.cube[UP][(self.cube[FRONT], 3)] = left[2]
  318.         self.cube[UP][(self.cube[FRONT], 4)] = left[1]
  319.         self.cube[UP][(self.cube[FRONT], 5)] = left[0]
  320.  
  321.         self.cube[LEFT][(self.cube[FRONT], 1)] = down[0]
  322.         self.cube[LEFT][(self.cube[FRONT], 4)] = down[1]
  323.         self.cube[LEFT][(self.cube[FRONT], 7)] = down[2]
  324.  
  325.         self.cube[DOWN][(self.cube[FRONT], 3)] = right[2]
  326.         self.cube[DOWN][(self.cube[FRONT], 4)] = right[1]
  327.         self.cube[DOWN][(self.cube[FRONT], 5)] = right[0]
  328.  
  329.         self.cube[RIGHT][(self.cube[FRONT], 1)] = up[0]
  330.         self.cube[RIGHT][(self.cube[FRONT], 4)] = up[1]
  331.         self.cube[RIGHT][(self.cube[FRONT], 7)] = up[2]
  332.        
  333.        
  334.        
  335.  
  336.     def randomize(self, turns = 1000):
  337.         sides = [self.FRONT, self.BACK, self.LEFT, self.RIGHT, self.UP, self.DOWN]
  338.         for i in xrange(turns):
  339.             if random.random() > .5:
  340.                 self.turn(random.choice(sides))
  341.             else:
  342.                 self.turnMiddle(random.choice(sides))
  343.                
  344.     def isSolved(self):
  345.         for s in self.cube:
  346.             if not self.cube[s].isSolved(): return False
  347.         return True
  348.  
  349.     def __str__(self):
  350.         x = ""
  351.         for l in self.cube:
  352.             x += l+" : "+str(self.cube[l])+"\n"
  353.         return x[:-1]
  354.         #return self.formatStr()
  355.  
  356.     def strSide(self, face, replCol=True):
  357.         x = """%i %i %i
  358. %i %i %i
  359. %i %i %i""" % (self.cube[face][0][0],self.cube[face][0][1],self.cube[face][0][2],
  360.                self.cube[face][1][0],self.cube[face][1][1],self.cube[face][1][2],
  361.                self.cube[face][2][0],self.cube[face][2][1],self.cube[face][2][2])
  362.         if replCol:
  363.             for col in self.colLet: x = x.replace(str(col), self.colLet[col])
  364.         return x
  365.        
  366.     def strCube(self,face=-1,replCol=True):
  367.         faces = self.getFaces(face)
  368.         o = "FBLRUD"
  369.        
  370.         x = """
  371.        U0 U1 U2
  372.        U3 U4 U5  
  373.        U6 U7 U8    
  374. L0 L1 L2  F0 F1 F2  R0 R1 R2  B0 B1 B2
  375. L3 L4 L5  F3 F4 F5  R3 R4 R5  B3 B4 B5
  376. L6 L7 L8  F6 F7 F8  R6 R7 R8  B6 B7 B8
  377.        D0 D1 D2
  378.        D3 D4 D5
  379.        D6 D7 D8
  380. """
  381.         j = 0
  382.         for face in faces:
  383.             for i in xrange(9):
  384.                 s = "%s%d" % (o[j], i)
  385.                 x = x.replace(s, str(self.cube[face][faces[0], i]))
  386.             j+=1
  387.  
  388.         if replCol:
  389.             for col in self.colLet: x = x.replace(str(col), self.colLet[col])
  390.  
  391.         return x
  392.  
  393.     def wrongWay(self,face=-1):
  394.         code = {"W":1,"O":2,"B":3,"R":4,"G":5,"Y":6}
  395.         o = "UFLBRD"
  396.         r = ""
  397.         for face in o:
  398.             for i in xrange(9):
  399.                 r += str(code[self.colLet[self.cube[face][self.FRONT, i]]])
  400.         return r
  401.        
  402.     def getColName(self, num):
  403.         return self.colLet[num]
  404.    
  405.     def __repr__(self):
  406.         return self.strCube("U")#self.lastFace)
  407.  
  408.     def primeCube(self, frontFace = -1):
  409.         if frontFace == -1: frontFace = self.FRONT
  410.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  411.         primeCol = self.cube[UP][(self.cube[FRONT], 8)]
  412.         isPrime = False
  413.         stFace = FRONT
  414.         i = 0
  415.         while self.cube[UP][(self.cube[FRONT], 8)] != self.cube[UP][(self.cube[FRONT], 4)] and i < 4:
  416.             self.turnMiddle(FRONT)
  417.             i+=1
  418.         if self.cube[UP][(self.cube[FRONT], 8)] != self.cube[UP][(self.cube[FRONT], 4)]:
  419.             i = 0
  420.             while self.cube[UP][(self.cube[FRONT], 8)] != self.cube[UP][(self.cube[FRONT], 4)] and i < 4:
  421.                 self.turnMiddle(LEFT)
  422.                 i += 1
  423.         if self.cube[UP][(self.cube[FRONT], 8)] == self.cube[UP][(self.cube[FRONT], 4)]:
  424.             return FRONT
  425.         else:
  426.             return False
  427.  
  428.     def cornerHasColsBR(self, frontFace, needColors):
  429.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  430.         colors = (self.cube[FRONT][(self.cube[FRONT], 8)],
  431.                 self.cube[RIGHT][(self.cube[FRONT], 6)],
  432.                 self.cube[DOWN][(self.cube[FRONT], 2)])
  433.         cnt = 0
  434.         for color in needColors:
  435.             if color in colors:
  436.                 cnt += 1
  437.         return cnt >= 2
  438.  
  439.     def cornerHasColsTR(self, frontFace, needColors):
  440.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  441.         colors = (self.cube[FRONT][(self.cube[FRONT], 2)],
  442.                 self.cube[RIGHT][(self.cube[FRONT], 0)],
  443.                 self.cube[UP][(self.cube[FRONT], 8)])
  444.         cnt = 0
  445.         for color in needColors:
  446.             if color in colors:
  447.                 cnt += 1
  448.         return cnt >= 2
  449.  
  450.     def cornerHasColsTL(self, frontFace, needColors):
  451.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  452.         colors = (self.cube[FRONT][(self.cube[FRONT], 0)],
  453.                 self.cube[LEFT][(self.cube[FRONT], 2)],
  454.                 self.cube[UP][(self.cube[FRONT], 6)])
  455.         cnt = 0
  456.         for color in needColors:
  457.             if color in colors:
  458.                 cnt += 1
  459.         return cnt >= 2
  460.  
  461.     def stepOneCompleteFace(self, frontFace, upCol):
  462.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  463.         f0 = self.cube[FRONT][(self.cube[FRONT], 0)]
  464.         f1 = self.cube[FRONT][(self.cube[FRONT], 2)]
  465.         u0 = self.cube[UP][(self.cube[FRONT], 6)]
  466.         u1 = self.cube[UP][(self.cube[FRONT], 8)]
  467.         return (u0 == upCol) and (u0 == u1) and (f0 == f1)
  468.    
  469.     def stepOne(self, frontFace=-1, check=True):
  470.         counter = 0
  471.         skip = []
  472.         completedFaces = []
  473.         if frontFace == -1: frontFace = self.FRONT
  474.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  475.         # Assume we just primed
  476.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  477.         upCol = self.cube[UP][(self.cube[FRONT], 4)]
  478.         skipCount = 0
  479.         while counter < 20 and len(completedFaces) < 4:
  480.  
  481.             if self.stepOneCompleteFace(FRONT, upCol):
  482.                 if FRONT not in completedFaces: completedFaces.append(FRONT)
  483.                 #print "%s is completed" % FRONT
  484.                 FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  485.                 continue
  486.             needCols = (upCol, self.cube[FRONT][self.cube[FRONT], 0])
  487.             if self.cube[FRONT][(self.cube[FRONT], 2)] == upCol and self.cornerHasColsTR(FRONT, needCols): # Algo 4
  488.                 #print "Using Algo 4"
  489.                 self.turn(FRONT)
  490.                 self.turn(DOWN)
  491.                 self.turn(FRONT, False)
  492.                 self.turn(DOWN)
  493.                 self.turn(DOWN)
  494.                 self.turn(RIGHT, False)
  495.                 self.turn(DOWN)
  496.                 self.turn(RIGHT)
  497.                 if self.stepOneCompleteFace(FRONT, upCol):
  498.                     completedFaces.append(FRONT)
  499.                 else:
  500.                     #print "Algo failed."
  501.                     FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  502.             elif self.cube[RIGHT][(self.cube[FRONT], 0)] == upCol and self.cornerHasColsTR(FRONT, needCols): # Algo 5
  503.                 #print "Using Algo 5"
  504.                 self.turn(RIGHT, False)
  505.                 self.turn(DOWN, False)
  506.                 self.turn(RIGHT)
  507.                 self.turn(DOWN)
  508.                 self.turn(RIGHT, False)
  509.                 self.turn(DOWN, False)
  510.                 self.turn(RIGHT)
  511.                 if self.stepOneCompleteFace(FRONT, upCol):
  512.                     completedFaces.append(FRONT)
  513.                 else:
  514.                     #print "Algo failed."
  515.                     FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  516.             else:
  517.                 foundCorner = True
  518.                 i = 0
  519.                 while not self.cornerHasColsBR(FRONT, needCols) and i < 4:
  520.                     self.turn(DOWN)
  521.                     i += 1
  522.                 if i == 4 and not self.cornerHasColsBR(FRONT, needCols):
  523.                     foundCorner = False
  524.                 if foundCorner and self.cube[RIGHT][(self.cube[FRONT], 6)] == upCol: # Algo 1
  525.                     #print "Using Algo 1"
  526.                     self.turn(RIGHT, False)
  527.                     self.turn(DOWN, False)
  528.                     self.turn(RIGHT)
  529.                    
  530.                     if self.stepOneCompleteFace(FRONT, upCol):
  531.                         completedFaces.append(FRONT)
  532.                     else:
  533.                         #print "Algo failed."
  534.                         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  535.                 elif foundCorner and self.cube[FRONT][(self.cube[FRONT], 8)] == upCol: # Algo 2
  536.                     #print "Using Algo 2"
  537.                     self.turn(DOWN, False)
  538.                     self.turn(RIGHT, False)
  539.                     self.turn(DOWN)
  540.                     self.turn(RIGHT)
  541.                     if self.stepOneCompleteFace(FRONT, upCol):
  542.                         completedFaces.append(FRONT)
  543.                     else:
  544.                         #print "Algo failed."
  545.                         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  546.                 elif foundCorner and self.cube[DOWN][(self.cube[FRONT], 2)] == upCol: # Algo 3
  547.                     #print "Using Algo 3"
  548.                     self.turn(RIGHT, False)
  549.                     self.turn(DOWN)
  550.                     self.turn(RIGHT)
  551.                     self.turn(DOWN)
  552.                     self.turn(DOWN)
  553.                     self.turn(RIGHT, False)
  554.                     self.turn(DOWN, False)
  555.                     self.turn(RIGHT)
  556.                     if self.stepOneCompleteFace(FRONT, upCol):
  557.                         completedFaces.append(FRONT)
  558.                     else:
  559.                         #print "Algo failed."
  560.                         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  561.                 else:
  562.                     #print "Skipping Face", FRONT
  563.                     skipCount += 1
  564.                     if skipCount == 3:
  565.                         self.turn(RIGHT)
  566.                         self.turn(DOWN)
  567.                         skipCount = 0
  568.                     #return False
  569.                     FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  570.             counter += 1
  571.         if self.stepOneComplete(FRONT):
  572.             self.lastFace = FRONT
  573.             return FRONT
  574.         elif check:
  575.             return self.stepOne(frontFace, False)
  576.         else:
  577.             return False
  578.  
  579.  
  580.     def stepOneComplete(self, frontFace):
  581.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  582.         midCol = self.cube[UP][(self.cube[UP], 4)]
  583.         if self.cube[UP][(self.cube[UP], 0)] != midCol: return False
  584.         if self.cube[UP][(self.cube[UP], 2)] != midCol: return False
  585.         if self.cube[UP][(self.cube[UP], 6)] != midCol: return False
  586.         if self.cube[UP][(self.cube[UP], 8)] != midCol: return False
  587.         for i in xrange(4):
  588.             if self.cube[FRONT][(self.cube[FRONT], 0)] != self.cube[FRONT][(self.cube[FRONT], 2)]: return False
  589.             FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  590.         return True
  591.  
  592.     def stepTwo(self, frontFace, check=True):
  593.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  594.         if not self.stepOneComplete(FRONT):
  595.             raise RuntimeError("Step 2 conditions not met.")
  596.         upCol = self.cube[UP][(self.cube[FRONT], 4)]
  597.  
  598.         i = 0
  599.         while not self.allFirstLayer(FRONT) and i < 128:
  600.             faceCol = self.cube[FRONT][(self.cube[FRONT], 0)]
  601.             if self.cube[DOWN][self.cube[FRONT], 1] == upCol and self.cube[FRONT][self.cube[FRONT], 7] == faceCol:
  602.                 self.turnMiddle(LEFT)
  603.                 self.turn(DOWN, False)
  604.                 self.turn(DOWN, False)
  605.                 self.turnMiddle(RIGHT)
  606.             elif self.cube[FRONT][self.cube[FRONT], 7] == upCol and self.cube[DOWN][self.cube[FRONT], 1] == faceCol:
  607.                 self.turn(DOWN, False)
  608.                 self.turnMiddle(LEFT)
  609.                 self.turn(DOWN)
  610.                 self.turnMiddle(RIGHT)
  611.             elif self.cube[RIGHT][self.cube[FRONT], 3] == upCol and self.cube[FRONT][self.cube[FRONT], 5] == faceCol:
  612.                 self.turnMiddle(DOWN)
  613.                 self.turn(FRONT)
  614.                 self.turnMiddle(UP)
  615.                 self.turn(FRONT, False)
  616.             elif self.cube[FRONT][self.cube[FRONT], 5] == upCol and self.cube[RIGHT][self.cube[FRONT], 3] == faceCol:
  617.                 self.turnMiddle(DOWN)
  618.                 self.turn(FRONT, False)
  619.                 self.turnMiddle(UP)
  620.                 self.turnMiddle(UP)
  621.                 self.turn(FRONT)
  622.             elif self.cube[FRONT][self.cube[FRONT], 1] == upCol and self.cube[UP][self.cube[FRONT], 7] == faceCol:
  623.                 self.turnMiddle(LEFT)
  624.                 self.turn(DOWN, False)
  625.                 self.turn(DOWN, False)
  626.                 self.turnMiddle(RIGHT)
  627.                 self.turn(DOWN, False)
  628.                 self.turnMiddle(LEFT)
  629.                 self.turn(DOWN)
  630.                 self.turnMiddle(RIGHT)
  631.             FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  632.             i += 1
  633.             if i % 4 == 0:
  634.                 self.turn(UP)
  635.  
  636.         if self.allFirstLayer(FRONT):
  637.             return FRONT
  638.         else:
  639.             return False
  640.  
  641.     def firstLayer(self, face):
  642.         r = True
  643.         lr = self.cube[face].listRep(face)[:3]
  644.         fc = lr[0]
  645.         for facelet in lr:
  646.             if facelet != fc: r = False; break
  647.         return r
  648.  
  649.     def allFirstLayer(self, frontFace):
  650.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  651.         for cFace in [FRONT, RIGHT, BACK, LEFT]:
  652.             if not self.firstLayer(cFace):
  653.                 return False
  654.         return True
  655.    
  656.     def firstTwoLayers(self, face):
  657.         r = True
  658.         lr = self.cube[face].listRep(face)[:6]
  659.         fc = lr[0]
  660.         for facelet in lr:
  661.             if facelet != fc: r = False; break
  662.         return r
  663.  
  664.     def allFirstTwoLayers(self, frontFace):
  665.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  666.         for cFace in [FRONT, RIGHT, BACK, LEFT]:
  667.             if not self.firstTwoLayers(cFace):
  668.                 return False
  669.         return True
  670.                
  671.     def stepThree(self, frontFace, check=True):
  672.         if not self.allFirstLayer(frontFace):
  673.             raise RuntimeError("Step 3 conditions not met.")
  674.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  675.         while self.cube[FRONT][self.cube[FRONT], 1] != self.cube[FRONT][self.cube[FRONT], 4]:
  676.             self.turnMiddle(UP)
  677.  
  678.         i = 0
  679.         j = 0
  680.         perf = False
  681.         while not self.allFirstTwoLayers(frontFace) and j < 64:
  682.             faceCol = self.cube[FRONT][(self.cube[FRONT], 4)]
  683.             leftCol = self.cube[LEFT][(self.cube[FRONT], 4)]
  684.             rightCol = self.cube[RIGHT][(self.cube[FRONT], 4)]
  685.             tCol = self.cube[FRONT][(self.cube[FRONT], 7)]
  686.             dCol = self.cube[DOWN][(self.cube[FRONT], 1)]
  687.             if tCol == faceCol:
  688.                 if dCol == leftCol:
  689.                     self.turn(DOWN)
  690.                     self.turn(LEFT)
  691.                     self.turn(DOWN, False)
  692.                     self.turn(LEFT, False)
  693.                     self.turn(DOWN, False)
  694.                     self.turn(FRONT, False)
  695.                     self.turn(DOWN)
  696.                     self.turn(FRONT)
  697.                     perf = True
  698.                 elif dCol == rightCol:
  699.                     self.turn(DOWN, False)
  700.                     self.turn(RIGHT, False)
  701.                     self.turn(DOWN)
  702.                     self.turn(RIGHT)
  703.                     self.turn(DOWN)
  704.                     self.turn(FRONT)
  705.                     self.turn(DOWN, False)
  706.                     self.turn(FRONT, False)
  707.                     perf = True
  708.             FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  709.             i += 1
  710.             if i % 4 == 0:
  711.                 j += 1
  712.                 if j % 4 == 0:
  713.                     F, B, L, R, U, D = self.getFaces(FRONT)
  714.                     for k in xrange(4):
  715.                         if self.cube[F][(self.cube[F], 3)] != self.cube[F][(self.cube[F], 4)] or \
  716.                            self.cube[L][(self.cube[F], 5)] != self.cube[L][(self.cube[F], 4)]:
  717.                             self.turn(D)
  718.                             self.turn(L)
  719.                             self.turn(D, False)
  720.                             self.turn(L, False)
  721.                             self.turn(D, False)
  722.                             self.turn(F, False)
  723.                             self.turn(D)
  724.                             self.turn(F)
  725.                             break
  726.                         elif self.cube[F][(self.cube[F], 5)] != self.cube[F][(self.cube[F], 4)] or \
  727.                              self.cube[R][(self.cube[F], 3)] != self.cube[R][(self.cube[F], 4)]:  
  728.                             self.turn(D, False)
  729.                             self.turn(R, False)
  730.                             self.turn(D)
  731.                             self.turn(R)
  732.                             self.turn(D)
  733.                             self.turn(F)
  734.                             self.turn(D, False)
  735.                             self.turn(F, False)
  736.                             break
  737.                         F, B, L, R, U, D = self.getFaces(R)
  738.                 else:
  739.                     self.turn(DOWN)
  740.                
  741.  
  742.         return FRONT if self.allFirstTwoLayers(frontFace) else False
  743.         faces = [FRONT, RIGHT, BACK, LEFT]
  744.         i = 0
  745.         tPossible = 0
  746.         while not self.allFirstTwoLayers(FRONT) and i < 40:
  747.             face = faces[i % 4]
  748.             F, B, L, R, U, D = self.getFaces(face)
  749.             #if tPossible == 0:
  750.             #    print face
  751.             tPossible += 1
  752.             j = 0
  753.             while j < 4:
  754.                 midCol = self.cube[F][self.cube[F], 4]
  755.                 if self.cube[F][self.cube[F], 7] == midCol and (self.cube[D][self.cube[F], 1] in (self.cube[L][self.cube[F], 4], self.cube[R][self.cube[F], 4])):
  756.                     tPossible = 0
  757.                     if self.cube[D][self.cube[F], 1] == self.cube[L][self.cube[F], 4]:
  758.                         self.turn(D)
  759.                         self.turn(L)
  760.                         self.turn(D, False)
  761.                         self.turn(L, False)
  762.                         self.turn(D, False)
  763.                         self.turn(F, False)
  764.                         self.turn(D)
  765.                         self.turn(F)
  766.                     elif self.cube[D][self.cube[F], 1] == self.cube[R][self.cube[F], 4]:
  767.                         self.turn(D, False)
  768.                         self.turn(R, False)
  769.                         self.turn(D)
  770.                         self.turn(R)
  771.                         self.turn(D)
  772.                         self.turn(F)
  773.                         self.turn(D, False)
  774.                         self.turn(F, False)
  775.                 else:
  776.                     self.turn(D)
  777.                     j += 1
  778.             if tPossible == 5:
  779.                 for face in faces:
  780.                     F, B, L, R, U, D = self.getFaces(face)
  781.                     midCol = self.cube[F][self.cube[F], 4]
  782.                     if self.cube[F][self.cube[F], 3] != midCol:
  783.                         self.turn(D)
  784.                         self.turn(L)
  785.                         self.turn(D, False)
  786.                         self.turn(L, False)
  787.                         self.turn(D, False)
  788.                         self.turn(F, False)
  789.                         self.turn(D)
  790.                         self.turn(F)
  791.                     elif self.cube[F][self.cube[F], 5] != midCol:
  792.                         self.turn(D, False)
  793.                         self.turn(R, False)
  794.                         self.turn(D)
  795.                         self.turn(R)
  796.                         self.turn(D)
  797.                         self.turn(F)
  798.                         self.turn(D, False)
  799.                         self.turn(F, False)
  800.                 tPossible = 0
  801.             i += 1
  802.         if self.allFirstTwoLayers(FRONT):
  803.             return FRONT
  804.         else:
  805.             if check:
  806.                 return self.stepThree(FRONT, False)
  807.             else:
  808.                 return False
  809.  
  810.     def switch1and2(self, frontFace):
  811.         F, B, L, R, U, D = self.getFaces(frontFace)
  812.         self.turn(L, False)
  813.         self.turn(U, False)
  814.         self.turn(L)
  815.         self.turn(F)
  816.         self.turn(U)
  817.         self.turn(F, False)
  818.         self.turn(L, False)
  819.         self.turn(U)
  820.         self.turn(L)
  821.         self.turn(U)
  822.         self.turn(U)
  823.  
  824.     def switch1and3(self, frontFace):
  825.         F, B, L, R, U, D = self.getFaces(frontFace)
  826.         self.turn(U)
  827.         self.turn(L, False)
  828.         self.turn(U, False)
  829.         self.turn(L)
  830.         self.turn(F)
  831.         self.turn(U)
  832.         self.turn(F, False)
  833.         self.turn(L, False)
  834.         self.turn(U)
  835.         self.turn(L)
  836.         self.turn(U)
  837.  
  838.     def colorPos1(self, frontFace):
  839.         F, B, L, R, U, D = self.getFaces(frontFace)
  840.         return (self.cube[F][(self.cube[F], 2)],
  841.                 self.cube[U][(self.cube[F], 8)],
  842.                 self.cube[R][(self.cube[F], 0)])
  843.  
  844.     def colorPos2(self, frontFace):
  845.         F, B, L, R, U, D = self.getFaces(frontFace)
  846.         return (self.cube[F][(self.cube[F], 0)],
  847.                 self.cube[U][(self.cube[F], 6)],
  848.                 self.cube[L][(self.cube[F], 2)])
  849.  
  850.     def colorPos3(self, frontFace):
  851.         F, B, L, R, U, D = self.getFaces(frontFace)
  852.         return (self.cube[R][(self.cube[F], 2)],
  853.                 self.cube[U][(self.cube[F], 2)],
  854.                 self.cube[B][(self.cube[F], 0)])
  855.  
  856.     def colorPos4(self, frontFace):
  857.         F, B, L, R, U, D = self.getFaces(frontFace)
  858.         return (self.cube[B][(self.cube[F], 2)],
  859.                 self.cube[U][(self.cube[F], 0)],
  860.                 self.cube[L][(self.cube[F], 0)])
  861.  
  862.     def sameColors(self, one, two):
  863.         for color in one:
  864.             if color not in two: return False
  865.         return True
  866.  
  867.     def stepFour(self, frontFace):
  868.         if not self.allFirstTwoLayers(frontFace):
  869.             raise RuntimeError("Step 4 conditions not met.")
  870.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  871.         self.turn(FRONT); self.turn(FRONT)
  872.         self.turnMiddle(FRONT); self.turnMiddle(FRONT)
  873.         self.turn(BACK, False); self.turn(BACK, False)
  874.  
  875.         upCol = self.cube[UP][(self.cube[FRONT], 4)]
  876.         needColors = (upCol, self.cube[FRONT][(self.cube[FRONT], 4)])
  877.  
  878.         order = [
  879.             (self.cube[FRONT][(self.cube[FRONT], 4)], self.cube[RIGHT][(self.cube[FRONT], 4)], self.cube[UP][(self.cube[FRONT], 4)]),
  880.             (self.cube[FRONT][(self.cube[FRONT], 4)], self.cube[LEFT][(self.cube[FRONT], 4)], self.cube[UP][(self.cube[FRONT], 4)]),
  881.             (self.cube[BACK][(self.cube[FRONT], 4)], self.cube[RIGHT][(self.cube[FRONT], 4)], self.cube[UP][(self.cube[FRONT], 4)]),
  882.             (self.cube[BACK][(self.cube[FRONT], 4)], self.cube[LEFT][(self.cube[FRONT], 4)], self.cube[UP][(self.cube[FRONT], 4)])
  883.         ]
  884.  
  885.         while not self.sameColors(self.colorPos4(FRONT), order[3]):
  886.             self.turn(UP)
  887.  
  888.         cube1 = self.colorPos1(FRONT)
  889.         cube4 = self.colorPos4(FRONT)
  890.         pos = 3
  891.         #for i in xrange(len(order)):
  892.         #    if self.sameColors(order[i], cube4):
  893.         #        pos = i
  894.         #        break
  895.         #print pos
  896.         if not self.sameColors(order[0], cube1):
  897.             if self.sameColors(self.colorPos2(FRONT), order[0]):
  898.                 self.switch1and2(FRONT)
  899.             elif self.sameColors(self.colorPos3(FRONT), order[0]):
  900.                 self.switch1and3(FRONT)
  901.             else:
  902.                 raise RuntimeError("Unexpected order?")
  903.  
  904.         #while not self.sameColors(self.colorPos1(FRONT), order[0]):
  905.         #    self.turn(UP)
  906.  
  907.         if not self.sameColors(order[1], self.colorPos2(FRONT)): # 2 and 3 are swapped
  908.             self.switch1and3(FRONT)
  909.             self.switch1and2(FRONT)
  910.             self.switch1and3(FRONT)
  911.            
  912.        
  913.         c = [self.colorPos1(FRONT),self.colorPos2(FRONT),self.colorPos3(FRONT),self.colorPos4(FRONT)]
  914.  
  915.         for o in xrange(len(order)):
  916.             if not self.sameColors(order[o], c[o]): print "FAILURE %d" % (o+1)
  917.  
  918.         while not self.sameColors(self.colorPos1(FRONT), order[0]):
  919.             self.turn(UP)
  920.  
  921.         return FRONT
  922.  
  923.     def modelOne(self, frontFace):
  924.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  925.         return self.cube[UP][(self.cube[FRONT], 4)] == self.cube[UP][(self.cube[FRONT], 8)] == \
  926.                self.cube[FRONT][(self.cube[FRONT], 0)]
  927.  
  928.     def modelTwo(self, frontFace):
  929.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  930.         return self.cube[UP][(self.cube[FRONT], 4)] == self.cube[RIGHT][(self.cube[FRONT], 0)] == \
  931.                self.cube[RIGHT][(self.cube[FRONT], 2)]
  932.  
  933.     def modelThree(self, frontFace):
  934.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  935.         return self.cube[UP][(self.cube[FRONT], 4)] == self.cube[UP][(self.cube[FRONT], 8)] == \
  936.                self.cube[RIGHT][(self.cube[FRONT], 2)];
  937.  
  938.     def stepFiveAlgo(self, frontFace):
  939.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  940.         self.turn(LEFT, False)
  941.         self.turn(UP, False)
  942.         self.turn(LEFT)
  943.         self.turn(UP, False)
  944.         self.turn(LEFT, False)
  945.         self.turn(UP, False)
  946.         self.turn(UP, False)
  947.         self.turn(LEFT)
  948.         self.turn(UP, False)
  949.         self.turn(UP, False)
  950.  
  951.     def upCornersDone(self, frontFace):
  952.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  953.         return self.cube[UP][(self.cube[FRONT], 0)] == self.cube[UP][(self.cube[FRONT], 2)] == \
  954.                self.cube[UP][(self.cube[FRONT], 4)] ==  self.cube[UP][(self.cube[FRONT], 6)] == \
  955.                 self.cube[UP][(self.cube[FRONT], 8)]
  956.                
  957.        
  958.     def stepFive(self, frontFace):
  959.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  960.         f = True
  961.         m1 = None
  962.         while True:
  963.             if self.modelOne(FRONT):
  964.                 m1 = 10
  965.                 break
  966.             elif self.modelTwo(FRONT):
  967.                 m1 = 20
  968.                 break
  969.             elif self.modelThree(FRONT):
  970.                 m1 = 30
  971.                 break
  972.             else:
  973.                 if f:
  974.                     self.stepFiveAlgo(FRONT)
  975.                     f = False
  976.                 FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  977.         self.stepFiveAlgo(FRONT)
  978.         while not self.upCornersDone(FRONT):
  979.             if self.modelOne(FRONT) and m1 != 1:
  980.                 self.stepFiveAlgo(FRONT)
  981.             elif self.modelTwo(FRONT) and m1 != 2:
  982.                 self.stepFiveAlgo(FRONT)
  983.             elif self.modelThree(FRONT) and m1 != 3:
  984.                 self.stepFiveAlgo(FRONT)
  985.             else:
  986.                 FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  987.         return FRONT
  988.  
  989.     def sixAlgo(self, frontFace):
  990.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  991.         self.turnMiddle(RIGHT)
  992.         self.turn(UP, False)
  993.         self.turnMiddle(LEFT)
  994.         self.turn(UP, False)
  995.         self.turn(UP, False)
  996.         self.turnMiddle(RIGHT)
  997.         self.turn(UP, False)
  998.         self.turnMiddle(LEFT)
  999.  
  1000.     def stepSix(self, frontFace):
  1001.         DEDH = 0
  1002.         FISH = 1
  1003.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  1004.         j = 0
  1005.         while not self.isSolved() and j < 15:
  1006.             pairs = []
  1007.             for i in xrange(4):
  1008.                 if self.cube[FRONT][(self.cube[FRONT], 1)] == self.cube[UP][(self.cube[FRONT], 4)] and \
  1009.                    self.cube[FRONT][(self.cube[FRONT], 4)] == self.cube[UP][(self.cube[FRONT], 7)] and \
  1010.                    (self.cube[UP][(self.cube[FRONT], 4)], self.cube[FRONT][(self.cube[FRONT], 4)]) not in pairs:
  1011.                     self.sixAlgo(FRONT)
  1012.                     pairs.append(self.cube[FRONT][(self.cube[FRONT], 4)])
  1013.                 FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  1014.             if len(pairs) == 0: self.sixAlgo(FRONT)
  1015.             pattern = None
  1016.             for i in xrange(4):
  1017.                 if self.cube[UP][(self.cube[FRONT], 7)] != self.cube[UP][(self.cube[FRONT], 4)] and \
  1018.                    self.cube[UP][(self.cube[FRONT], 5)] != self.cube[UP][(self.cube[FRONT], 4)]:
  1019.                     pattern = FISH
  1020.                     break
  1021.                 elif self.cube[UP][(self.cube[FRONT], 3)] != self.cube[UP][(self.cube[FRONT], 4)] and \
  1022.                      self.cube[UP][(self.cube[FRONT], 5)] != self.cube[UP][(self.cube[FRONT], 4)]:
  1023.                     pattern = DEDH
  1024.                     break
  1025.                 FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  1026.             if pattern == FISH:
  1027.                 self.dedmoreFish(FRONT)
  1028.             else:
  1029.                 self.dedmoreH(FRONT)
  1030.             if not self.isSolved():
  1031.                 self.dedmoreH(FRONT)
  1032.             j += 1
  1033.  
  1034.         return self.isSolved()
  1035.  
  1036.     def solveCube(self):
  1037.         self.startRecord()
  1038.         faces = [self.FRONT, self.DOWN, self.BACK, self.UP, self.LEFT, self.RIGHT]
  1039.         for i in xrange(50):
  1040.             if (i+1) % 3 == 0: self.randomize(5)
  1041.             if self.isSolved(): break
  1042.             s = self.primeCube(faces[i % len(faces)])
  1043.             if not s:
  1044.                 continue
  1045.             if self.isSolved(): break
  1046.             s = self.stepOne(s)
  1047.             if not s:
  1048.                 continue
  1049.             if self.isSolved(): break
  1050.             s = self.stepTwo(s)
  1051.             if not s:
  1052.                 continue
  1053.             if self.isSolved(): break
  1054.             s = self.stepThree(s)
  1055.             if not s:
  1056.                 continue
  1057.             if self.isSolved(): break
  1058.             s = self.stepFour(s)
  1059.             if not s:
  1060.                 continue
  1061.             if self.isSolved(): break
  1062.             s = self.stepFive(s)
  1063.             if not s:
  1064.                 continue
  1065.             if self.isSolved(): break
  1066.             s = self.stepSix(s)
  1067.             if not s:
  1068.                 continue
  1069.             if self.isSolved(): break
  1070.         self.endRecord()
  1071.         if self.isSolved():
  1072.             print "Solved in %d moves." % len(self.moveList)
  1073.             print "".join(self.moveList)
  1074.         return self.isSolved()
  1075.  
  1076.     def dedmoreH(self, frontFace):
  1077.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  1078.         self.turn(RIGHT, False)
  1079.         self.turnMiddle(UP)
  1080.         self.turn(RIGHT, False)
  1081.         self.turn(RIGHT, False)
  1082.         self.turnMiddle(UP)
  1083.         self.turnMiddle(UP)
  1084.         self.turn(RIGHT, False)
  1085.         self.turn(UP, False)
  1086.         self.turn(UP, False)
  1087.         self.turn(RIGHT)
  1088.         self.turnMiddle(DOWN)
  1089.         self.turnMiddle(DOWN)
  1090.         self.turn(RIGHT, False)
  1091.         self.turn(RIGHT, False)
  1092.         self.turnMiddle(DOWN)
  1093.         self.turn(RIGHT)
  1094.         self.turn(UP, False)
  1095.         self.turn(UP, False)
  1096.  
  1097.     def dedmoreFish(self, frontFace):
  1098.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  1099.         self.turn(FRONT, False)
  1100.         self.turn(LEFT, False)
  1101.         self.turn(RIGHT, False)
  1102.         self.turnMiddle(UP)
  1103.         self.turn(RIGHT, False)
  1104.         self.turn(RIGHT, False)
  1105.         self.turnMiddle(UP)
  1106.         self.turnMiddle(UP)
  1107.         self.turn(RIGHT, False)
  1108.         self.turn(UP, False)
  1109.         self.turn(UP, False)
  1110.         self.turn(RIGHT)
  1111.         self.turnMiddle(DOWN)
  1112.         self.turnMiddle(DOWN)
  1113.         self.turn(RIGHT, False)
  1114.         self.turn(RIGHT, False)
  1115.         self.turnMiddle(DOWN)
  1116.         self.turn(RIGHT)
  1117.         self.turn(UP, False)
  1118.         self.turn(UP, False)
  1119.         self.turn(LEFT)
  1120.         self.turn(FRONT)
  1121.  
  1122.     def stepSeven(self, frontFace):
  1123.         FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(frontFace)
  1124.         FISH = 0
  1125.         DEDH = 1
  1126.         pattern = None
  1127.  
  1128.         numFlipped = 0
  1129.         for i in xrange(4):
  1130.             if self.cube[UP][(self.cube[FRONT], 7)] != self.cube[UP][(self.cube[FRONT], 4)] or \
  1131.                self.cube[FRONT][(self.cube[FRONT], 1)] != self.cube[FRONT][(self.cube[FRONT], 0)]:
  1132.                 numFlipped += 1
  1133.         print numFlipped
  1134.         if numFlipped > 2:
  1135.             self.dedmoreH(FRONT)
  1136.  
  1137.             FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  1138.  
  1139.         while pattern == None:
  1140.             for i in xrange(4):
  1141.                 if self.cube[UP][(self.cube[FRONT], 7)] != self.cube[UP][(self.cube[FRONT], 4)] and \
  1142.                    self.cube[UP][(self.cube[FRONT], 5)] != self.cube[UP][(self.cube[FRONT], 4)]:
  1143.                     pattern = FISH
  1144.                     break
  1145.                 elif self.cube[UP][(self.cube[FRONT], 3)] != self.cube[UP][(self.cube[FRONT], 4)] and \
  1146.                      self.cube[UP][(self.cube[FRONT], 5)] != self.cube[UP][(self.cube[FRONT], 4)]:
  1147.                     pattern = DEDH
  1148.                     break
  1149.                 FRONT, BACK, LEFT, RIGHT, UP, DOWN = self.getFaces(RIGHT)
  1150.             if pattern == None:
  1151.                 self.dedmoreH(FRONT)
  1152.         if pattern == FISH:
  1153.             self.dedmoreFish(FRONT)
  1154.         elif pattern == DEDH:
  1155.             self.dedmoreH(FRONT)
  1156.            
  1157. if __name__ == "__main__":
  1158.     print "Rubik's Cube Solver"
  1159.     print "Type v to view the cube"
  1160.     print "Type r to randomize the cube"
  1161.     print "Type s to solve the cube"
  1162.     print "Type q to quit"
  1163.     c = cube()
  1164.     command = ""
  1165.     while command != "q":
  1166.         command = raw_input(">>> ")[0].lower()
  1167.         if command == "v":
  1168.             print c.strCube()
  1169.         elif command == "r":
  1170.             c.randomize()
  1171.             print "Cube randomized"
  1172.         elif command == "s":
  1173.             c.solveCube()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement