fork download
  1. from __future__ import division
  2. from itertools import * # your code goes here
  3.  
  4. data = [('Plate 1',[('A',i) for i in range(92)]),
  5. ('Plate 2',[('A',i) for i in range(92)]),
  6. ('Plate 3',[('A',i) for i in range(64)]),
  7. ('Plate 4',[('A',i) for i in range(42)]+[('B',j) for j in range(42,92)]),
  8. ('Plate 5',[('A',i) for i in range(12)]+[('B',j) for j in range(12,61)]),
  9. ('Plate 6',[('B',i) for i in range(92)])]
  10.  
  11. # make data longer - note the solution will still be the same as we're adding in
  12. # exactly the same ratio
  13. #data = data + [d for d in data] + [d for d in data]
  14.  
  15. def powerset_no_empty(iterable):
  16. s = list(iterable)
  17. return chain.from_iterable(combinations(s, r) for r in range(1,len(s)+1))
  18.  
  19. tot_types = 0
  20. tot_A = 0
  21. for name,samples in data:
  22. tot_types += len(samples)
  23. tot_A += len([t for t in samples if t[0]=='A'])
  24.  
  25. #calculate the target ratio for each bin
  26. ratio_A = tot_A / tot_types # note ratio_B = 1.0 - ratio_A
  27.  
  28. p = powerset_no_empty(data)
  29.  
  30. scores = []
  31. comb_ratios = []
  32. num_batch_list = []
  33. comb_list = []
  34. print(p)
  35. for j in p:
  36. batch_types = 0
  37. batch_A = 0
  38. for name,samples in j:
  39. batch_types += len(samples)
  40. batch_A += len([t for t in samples if t[0]=='A'])
  41.  
  42. batch_ratio = batch_A/batch_types
  43. num_batches = int(batch_types/(3*92)+1)
  44.  
  45. #You might want to change the line below to weight nearness of ratio
  46. #and number of batches differently in the group score
  47. score = abs(batch_ratio - ratio_A) + num_batches
  48. comb_ratios.append(batch_ratio)
  49. num_batch_list.append(num_batches)
  50. scores.append(score)
  51. comb_list.append(j)
  52.  
  53. ranked_combs = sorted(zip(scores,comb_ratios,num_batch_list,comb_list))
  54.  
  55. plate_list = [k[0] for k in ranked_combs[0][3]]
  56. print('Best combination found was using {} in {} batches'.format(plate_list,ranked_combs[0][2]))
  57.  
  58. #for score, ratio, batches, combo in ranked_combs:
  59. # print(score, ratio, batches, [k[0] for k in combo])# your code goes here
Success #stdin #stdout 0.01s 7736KB
stdin
Standard input is empty
stdout
<itertools.chain object at 0xb741aa0c>
Best combination found was using ['Plate 3', 'Plate 5'] in 1 batches