 # surprising-challenge-generating-comprehensive-python-list.py

Dec 15th, 2016
113
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
1. from itertools import permutations, combinations_with_replacement
2.
3. _profiling = True  # profiling toggle
4.
5. if _profiling:
6.     from cProfile import Profile
7.     from pstats import Stats
8.     prof = Profile()
9.     prof.disable()
10.
12.     """
13.    Self-explanitory...
14.    """
15.     #print potential_structure
16.
17.     new_layers = [] # List to hold re-cast structure
18.     for layer in potential_structure:
19.         if len(new_layers) > 0: # if not the first item in the list of layers
20.             last_layer=new_layers[-1] # last element of existing layer list
21.             if layer == last_layer: # true is the two layers are the same material
22.                 combined_layer = (layer, layer + last_layer)
23.                 new_layers[len(new_layers)-1] = combined_layer
24.             else: # adjcent layers are different material so no comibantion is possible
25.                 new_layers.append(layer)
26.         else: # for the first layer
27.             new_layers.append(layer)
28.
29.     return tuple(new_layers)
30.
31. def calculate_unique_structure_lengths(thicknesses, materials, maximum_number_of_layers,\
32.                                        maximum_individual_layer_thicknesses, \
33.                                        maximum_total_material_thicknesses):
34.     """
35.    Create a set on all possible multilayer combinations.
36.
37.    thicknesses : if this contains '0' the total number of layers will vary
38.                  from 0 to maximum_number_of_layers, otherwise, the
39.                  number total number layers will always be maximum_number_of_layers
40.                  e.g. arange(0 , 100, 5)
41.
42.    materials : list of materials used
43.                e.g. ['Metal', 'Dielectric']
44.
45.    maximum_number_of_layers : pretty self-explanitory...
46.                               e.g. 5
47.
48.    maximum_individual_layer_thicknesses : filters the created the multilayer structures
49.                                           preventing the inclusion layers that are too thick
50.                                           - this is important after the joining of
52.                                           e.g. (('Metal',30),('Dielectric',20))
53.
54.    maximum_total_material_thicknesses : similar to the above but filters structures where the total
55.                                         amount of a particular material is exceeded
56.                                         e.g. (('Metal',50),('Dielectric',100))
57.
58.
59.    """
60.     # generate all possible thickness combinations and material combinations
61.     all_possible_thickness_sets = set(permutations(combinations_with_replacement(thicknesses, maximum_number_of_layers)))
62.     all_possible_layer_material_orders = set(permutations(combinations_with_replacement(materials, maximum_number_of_layers)))
63.
64.
65.     first_set = set() # Create set object (list of unique elements, no repeats)
66.     for layer_material_order in all_possible_layer_material_orders:
67.         for layer_thickness_set in all_possible_thickness_sets:
68.             potential_structure = [] # list to hold this structure
69.             for layer, thickness in zip(layer_material_order, layer_thickness_set): # combine the layer thickness with its material
70.                 if thickness != 0: # layers of zero thickness are not added to potential_structure
71.                     potential_structure.append((layer, thickness))
73.
74.     #print('first_set')
75.     #for struct in first_set:
76.     #    print struct
77.
78.     ## join adjacent repeated materials
79.     second_set = set() # create new set
80.     for potential_structure in first_set:
82.
83.     ## remove structures where a layer is too thick
84.     third_set = set()
85.     for potential_structure in second_set: # check all the structures in the set
86.         conditions_satisfied=True # default
87.         for max_condition in maximum_individual_layer_thicknesses: # check this structure using each condition
88.             for layer in potential_structure: # examine each layer
89.                 if layer == max_condition: # match condition with material
90.                     if layer > max_condition: # test thickness condition
91.                         conditions_satisfied=False
92.         if conditions_satisfied:
94.
95.     ##remove structures that contain too much of a certain material
96.     fourth_set = set()
97.     for potential_structure in second_set: # check all the structures in the set
98.         conditions_satisfied=True # default
99.         for max_condition in maximum_total_material_thicknesses: # check this structure using each condition
100.             amount_of_material_in_this_structure = 0 # initialise a counter
101.             for layer in potential_structure: # examine each layer
102.                 if layer == max_condition: # match condition with material
103.                     amount_of_material_in_this_structure += layer
104.                     if amount_of_material_in_this_structure > max_condition: # test thickness condition
105.                         conditions_satisfied=False
106.         if conditions_satisfied:
108.
109.     return fourth_set
110.
111. thicknesses = [0,1,2]
112. materials = ('A', 'B') # Tuple cannot be accidentally appended to later
113. maximum_number_of_layers = 3
114. maximum_individual_layer_thicknesses=(('A',30),('B',20))
115. maximum_total_material_thicknesses=(('A',20),('B',15))
116.
117. if _profiling:
118.     prof.enable()
119.
120. calculate_unique_structure_lengths(thicknesses, materials, maximum_number_of_layers,\
121.                                    maximum_individual_layer_thicknesses = maximum_individual_layer_thicknesses, \
122.                                    maximum_total_material_thicknesses = maximum_total_material_thicknesses)
123.
124. if _profiling:
125.     prof.disable()
126.     prof.dump_stats('unique.stats')
127.     with open('unique_stats.txt', 'wt') as output:
128.         stats = Stats('unique.stats', stream=output)
129.         stats.strip_dirs().sort_stats('cumulative', 'time')
130.         stats.sort_stats('cumulative', 'time')
131.         stats.print_stats()
RAW Paste Data