Advertisement
Guest User

sanitycheck.py

a guest
Jul 19th, 2019
430
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.40 KB | None | 0 0
  1. import re
  2.  
  3. # Parses ostr into a list of boards
  4. def parse(instr, ostr):
  5.     numlines = instr.count('\n')+1
  6.     i = 0
  7.     boards = []
  8.  
  9.     # Kinda hacky solution of counting each numlines lines as a board, due to flexible delimiting
  10.     while i<len(ostr):
  11.         currboard = ''
  12.         for _ in range(numlines):
  13.             if i>=len(ostr):
  14.                 print("Incorrect formatting -- can't parse boards; weird number of non-empty lines")
  15.                 exit(0)
  16.             currboard += '\n' + ostr[i]
  17.             i += 1
  18.         boards.append(currboard.strip())
  19.  
  20.     return boards
  21.  
  22. # Makes sure the board is of the correct format
  23. def check_format(instr, board):
  24.     regex = instr.replace('v', '[v^]')
  25.     return re.fullmatch(regex.strip(), board.strip())
  26.  
  27. # Util function for check_combinations
  28. def board_to_bitarray(board):
  29.     switches = re.sub(r'[\n\-]', '', board)
  30.     switches = switches.replace('v', '0').replace('^', '1')
  31.     return int(switches, 2)
  32.  
  33. # Makes sure we have all of the boards
  34. def check_combinations(boards, numswitches):
  35.     allnums = range(2**numswitches)
  36.     counts = {num:0 for num in allnums}
  37.     for board in boards:
  38.         counts[board_to_bitarray(board)] += 1
  39.    
  40.     missings = [num for num in allnums if counts[num]==0]
  41.     extras = {num:counts[num] for num in allnums if counts[num]>1}
  42.  
  43.     return missings, extras
  44.  
  45. # Util for more useful error messages
  46. # [bitarray_to_board(i, instr) for i in range(2**instr.count('v'))] is actually a valid solution to this challenge
  47. def bitarray_to_board(bitarray, instr):
  48.     swidxs = [match.start() for match in re.finditer('v', instr)]
  49.     newboard = [char for char in instr] # because python strings are immutable
  50.  
  51.     while bitarray!=0: # flip switches by bitshifting
  52.         currbit = bitarray & 1
  53.         if currbit:
  54.             newboard[swidxs[-1]] = '^'
  55.         swidxs = swidxs[:-1]
  56.         bitarray = bitarray >> 1
  57.  
  58.     return ''.join(newboard)
  59.  
  60. if __name__=='__main__':
  61.     # Get input and output
  62.     with open('input') as fi:
  63.         instr = fi.read()
  64.     with open('output') as fo:
  65.         ostr = fo.readlines()
  66.     ostr = [line.strip() for line in ostr if not line=='\n']
  67.  
  68.     # Read boards from output; check for formatting
  69.     boards = parse(instr, ostr)
  70.     for idx, board in enumerate(boards):
  71.         if not check_format(instr, board):
  72.             print('Board incorrectly formatted:\n' + board
  73.                     + ' starting at line ' + str(idx*(instr.count('\n')+1)+1) + '\n')
  74.             exit(0)
  75.    
  76.     # Check for correctness
  77.     missings, extras = check_combinations(boards, instr.count('v'))
  78.     if len(missings) > 0:
  79.         for bitarray in missings:
  80.             print('Missing board:\n' + bitarray_to_board(bitarray, instr) + '\n')
  81.     if len(extras) > 0:
  82.         for bitarray, count in extras.items():
  83.             print('Extra boards:\n' + bitarray_to_board(bitarray, instr)
  84.                     + ' appeared ' + str(count) + ' times\n')
  85.     if len(missings)==0 and len(extras)==0:
  86.         print('All correct!')
  87.  
  88.     # Sample solution
  89.     # with open('input') as fi:
  90.     #     instr = fi.read()
  91.     # with open('output', 'w') as fo:
  92.     #     boards = [bitarray_to_board(i, instr) for i in range(2**instr.count('v'))]
  93.     #     boards_formatted = [board + '\n\n' for board in boards]
  94.     #     fo.writelines(boards_formatted)
  95.     #     for board in boards_formatted: print(board)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement