示例#1
0
 def run_restoration_model(self, sequence=None):
     self.restoration = RestorationModel(self.graph_damaged, self.filepath)
     self.restoration.run(sequence)
     self.restoration_graphs = self.restoration.get_restoration_graphs()
     self.restoration_times = self.restoration.get_restoration_times()
     self.restoration_costs = self.restoration.get_restoration_costs()
     pass
示例#2
0
    def run(self):
        self.initialize_network()
        self.initialize_damage()
        init_state = self.initialize_state()

        no_damage = self.run_traffic_model(self.graph, self.od_graph)
        initial_damage = self.run_traffic_model(self.graph_damaged.copy(),
                                                self.od_graph.copy())

        damage = [no_damage, initial_damage]

        optimize = SimAnnealer(init_state, self.graph, self.od_graph,
                               self.od_matrix, self.graph_damaged, damage,
                               self.output_directory)

        optimize.copy_strategy = "slice"

        state, e = optimize.anneal()

        print("consequences: %i" % e)

        self.restoration_results = RestorationModel(self.graph_damaged)
        # (object,schedule time,needed time,#resources,intervention type, assignd resource)
        sequence_formated = self.restoration_results.format(state)

        with open(self.output_directory + 'state.txt', 'w') as f:
            f.write(str(state))

        with open(self.output_directory + 'state_formated.txt', 'w') as f:
            f.write(str(sequence_formated))
        pass
示例#3
0
    def run(self):
        """
        This function is used to run the Engine class (optimization of the restoration programs) on the object
        that was constructed from the Engine class.

        This is the main function of the Engine class that includes the following methods, and classes:

            methods:
            -------
                initialize_network
                initialize_damage
                initialize_state
                run_traffic_model
                anneal

        Class:
        SimAnnealInterface(init_state, self.graph, self.od_graph,self.od_matrix, self.graph_damaged, damage,
        self.output_directory)
        TODO: write more info here for SA

        """
        self.initialize_network()
        self.initialize_damage()
        init_state = self.initialize_state()

        # getting t_k, flow, hours, distances, lost_trips by running the traffic model before damage
        no_damage = self.run_traffic_model(self.graph, self.od_graph)

        # getting t_k, flow, hours, distances, lost_trips by running the traffic model after damage
        initial_damage = self.run_traffic_model(self.graph_damaged.copy(),
                                                self.od_graph.copy())

        damage = [no_damage, initial_damage]

        optimize = SimAnnealInterface(init_state, self.graph, self.od_graph,
                                      self.od_matrix, self.graph_damaged,
                                      damage, self.output_directory)

        optimize.copy_strategy = "slice"

        state, e = optimize.anneal(
        )  # Minimizes the energy of a system by simulated annealing

        print("consequences: %i" % e)

        self.restoration_results = RestorationModel(self.graph_damaged)

        # (object,schedule time (when it's finished),needed time,# of resources,intervention type, assignd resource)
        sequence_formated = self.restoration_results.format(state)

        with open(self.output_directory + 'state.txt', 'w') as f:
            f.write(str(state))

        with open(self.output_directory + 'state_formated.txt', 'w') as f:
            f.write(str(sequence_formated))
        pass
示例#4
0
    def energy(self):
        """Calculates the costs of the restoration."""
        e = 0

        restoration = RestorationModel(self.graph_damaged)
        restoration.run(self.state)
        restoration_graphs = restoration.get_restoration_graphs()
        restoration_times = restoration.get_restoration_times()
        restoration_costs = restoration.get_restoration_costs()

        damaged = []
        damaged.append(get_delta(self.no_damage, self.initial_damage))

        sim_results = Parallel(n_jobs=4)(
            delayed(parallel_model)(graph, self.od_graph, self.od_matrix)
            for graph in restoration_graphs[:-1])
        for values in sim_results:
            damaged.append(get_delta(self.no_damage, values))

        for idx, values in enumerate(damaged):
            dt = restoration_times[idx] if idx == 0 else restoration_times[idx] - \
                restoration_times[idx-1]
            e += sum(restoration_costs[idx]) + dt * (
                self.day_factor * values[2] * np.sum(self.mu * self.xi) +
                values[3] * np.sum(self.mu * (self.nu * self.F_w + self.rho)) +
                values[4] * self.upsilon)
        with open(self.fdir + 'energy.csv', 'a') as f:
            f.write('\n' + str(e))

        return e
示例#5
0
    def run(self, scenario):
        print('--- initialization ---')
        self.initialize_network()
        self.initialize_damage()
        init_state = self.load_state(self.filepath + 'state.txt')

        print('--- calculate damage ---')
        if not os.path.isfile(self.filepath + 'damaged.txt'):
            self.calculate_damage()
        else:
            self.damaged = self.load_damage(self.filepath + 'damaged.txt')

        # t_k, flow, hours, distances, lost_trips
        names_dict = {}
        for object in init_state:
            names_dict[object[0]] = get_edge_attribute(
                self.graph, object[0], 'name') + '-' + get_edge_attribute(
                    self.graph, object[0], 'object')[0]

        self.restoration_results = RestorationModel(self.graph_damaged,
                                                    self.filepath)
        # (object,schedule time,needed time,#resources,intervention type, assigned resource)
        sequence_formated = self.restoration_results.format(init_state)

        sort_names = []
        for s in sequence_formated:
            for t in s:
                sort_names.append([
                    t[1] - t[2], t[-1],
                    get_edge_attribute(self.graph, t[0], 'name')[2:]
                ])

        # remove dopples
        seen = set()
        sort_names = [
            x for x in sort_names if x[2] not in seen and not seen.add(x[2])
        ]
        sort_names = sorted(sort_names, key=itemgetter(1))
        sort_names = sorted(sort_names, key=itemgetter(0))

        name_dict = {}
        for name, key in enumerate(sort_names):
            name_dict[key[2]] = str(name + 1)

        print(name_dict)

        #name_dict = {'b-d': '1', ':a-g': '2', 'd-g': '3', 'd-e': '4'}
        # Keys: Object ID , Values: Nr in the table (8) of the paper
        # name_dict = {'1095': '6', '460': '10', '1703': '14', '1237': '20', '562': '11', '2069': '12', '1798': '24', '471': '28', '1371': '29', '1692': '15', '2043': '26', '1802': '8', '1907': '18', '1233': '23',
        #               '1913': '13', '2042': '1', '2052': '7', '2131': '17', '554': '2', '1276': '21', '1202': '22', '1706': '9', '1803': '5', '1905': '19', '1279': '16', '1814': '25', '332': '3', '1498': '27', '461': '4'}

        i = 0
        lines = []

        # TODO : is this  extra? I do not find any other places it is used
        name_list = []
        for s in sequence_formated:
            for t in s:
                name_list.append(
                    get_edge_attribute(self.graph, t[0], 'name')[2:])

        new_name_list = []
        for name in name_list:
            if name not in new_name_list:
                new_name_list.append(name)

        name_list = list(set(name_list))

        program_list = []
        for s in sequence_formated:
            for t in s:
                crew = t[5]
                task_end = t[1]
                task_duration = t[2]
                task_start = task_end - task_duration
                object_type = get_edge_attribute(self.graph, t[0], 'object')
                damage = get_edge_attribute(self.graph, t[0], 'damage')

                condition_state = {1: 'cs1', 2: 'cs2'}
                intervention_type = {
                    10: 'cs1i0',
                    11: 'cs1i1',
                    12: 'cs1i2',
                    20: 'cs2i0',
                    21: 'cs2i1',
                    22: 'cs2i2'
                }
                resources = {1: 'res1', 2: 'res2'}
                x_scale = .4012 / 2
                y_scale = .45
                start_point = (task_start * x_scale, crew * y_scale)
                end_point = (task_end * x_scale, (crew + 1) * y_scale)
                name = get_edge_attribute(self.graph, t[0], 'name')[2:]
                lines.append('\draw[normal,' + resources[t[3]] + ',' +
                             condition_state[damage] + ',' +
                             intervention_type[int(str(damage) + str(t[4]))] +
                             '] ' + str(start_point) + ' rectangle ' +
                             str(end_point) + ' node[mynode,pos=.5] {' +
                             name_dict[name] + ' \\\ ' + object_type[0] + '};')
                #lines.append('\draw[normal,'+resources[t[3]]+','+condition_state[damage]+','+intervention_type[int(str(damage)+str(t[4]))]+'] '+str(start_point)+' rectangle '+str(end_point)+ ' node[mynode,pos=.5] {'+name+' \\\ '+object_type[0]+'};')

                condition_state = {1: '1 minor', 2: '2 major'}
                intervention_type = {
                    10: 'level 1',
                    11: 'level 2',
                    12: 'level 3',
                    20: 'level 1',
                    21: 'level 2',
                    22: 'level 3'
                }
                intervention_nr = {
                    10: 'i',
                    11: 'ii',
                    12: 'iii',
                    20: 'i',
                    21: 'ii',
                    22: 'iii'
                }
                crew_type = {0: 'A', 1: 'B', 2: 'C'}
                sp = ' & '
                nl = '\\'

                program_list.append([
                    int(name_dict[name]), name, object_type,
                    condition_state[damage],
                    intervention_type[int(str(damage) + str(t[4]))],
                    str(task_start / 2),
                    str(task_end / 2),
                    str(task_duration / 2), crew_type[crew]
                ])
                # print(name_dict[name]+sp+name+sp+object_type+sp+condition_state[damage]+sp+intervention_nr[int(str(damage)+str(t[4]))]+sp+intervention_type[int(str(damage)+str(t[4]))]+sp+str(task_start/2)+sp+str(task_end/2)+sp+str(task_duration/2)+sp+crew_type[crew]+sp)
                i += 1

        costs_list = self.load_costs(self.filepath + 'costs.txt')
        for row in costs_list:
            del row[0]

        for i, l in enumerate(program_list):
            a = int(round(costs_list[i][0], 0))
            b = int(round(costs_list[i][1], 0))
            c = int(round(costs_list[i][2], 0))
            d = a + b + c
            l.extend([a, b, c, d])

        seen = set()
        program = [
            x for x in program_list if x[0] not in seen and not seen.add(x[0])
        ]

        sum_fixed = sum(row[-4] for row in program)
        sum_variable = sum(row[-3] for row in program)
        sum_resources = sum(row[-2] for row in program)
        sum_total = sum(row[-1] for row in program)

        program.sort(key=lambda x: x[0])

        program.append([
            '', '', '', '', '', '', '', '', '', sum_fixed, sum_variable,
            sum_resources, sum_total
        ])

        if not os.path.exists(self.filepath + 'tex/'):
            os.makedirs(self.filepath + 'tex/')
            print("Path is created")

        with open(self.filepath + 'tex/program_0' + scenario + '.tex',
                  mode='wt',
                  encoding='utf-8') as f:
            for p in program:
                for i in range(9, 13):
                    p[i] = '\\numprint{' + str(p[i]) + '}'
                f.write(' & '.join(str(e) for e in p) + ' \\\ \n')

        # TODO: I commented this part to avoid double results *check again for other figures
        # with open(self.filepath + 'tex/resources_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/resources_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        #print('t_k, flow, hours, distances, lost_trips')
        # for damage in damaged:
        #     print(damage)
        # TODO: What are these I do not think they are needed!
        fix_costs = [0]
        variable_costs = [0]
        resources_costs = [0]
        all_costs = [0]
        time = [0]

        self.run_restoration_model(init_state)

        #print(self.restoration_costs)

        # print(self.damaged)
        result_matrix = np.zeros((9, len(self.damaged) + 1))
        result_matrix_t = np.zeros((3, len(self.damaged) + 1))
        x = np.zeros(len(self.damaged) + 1)

        self.consequences = []
        for idx, damage in enumerate(self.damaged):
            if idx == 0:
                delta_t = self.restoration_times[idx]
            else:
                delta_t = (self.restoration_times[idx] -
                           self.restoration_times[idx - 1])

            result_matrix[0][idx + 1] = self.restoration_costs[idx][0]
            result_matrix[1][idx + 1] = self.restoration_costs[idx][1]
            result_matrix[2][idx + 1] = self.restoration_costs[idx][2]

            result_matrix[4][idx + 1] = (damage[2] * np.sum(
                self.mu * self.xi)) * delta_t * self.day_factor
            result_matrix[5][idx + 1] = (
                damage[3] * np.sum(self.mu *
                                   (self.nu * self.F_w + self.rho))) * delta_t
            result_matrix[6][idx + 1] = (damage[4] * self.upsilon) * delta_t

            result_matrix_t[0][idx + 1] = damage[2]
            result_matrix_t[1][idx + 1] = damage[3]
            result_matrix_t[2][idx + 1] = damage[4]

            #            print(damage[2], delta_t * (damage[2] * np.sum(self.mu*self.xi)))
            #            print(damage[3], delta_t * (damage[3] * np.sum(self.mu * (self.nu * self.F_w + self.rho))))
            #            print(damage[4], delta_t * (damage[4] * self.upsilon))
            #            print(damage[2])
            x[idx + 1] = self.restoration_times[idx]

            self.consequences.append(
                self.gamma * delta_t *
                (self.day_factor * damage[2] * np.sum(self.mu * self.xi) +
                 damage[3] * np.sum(self.mu *
                                    (self.nu * self.F_w + self.rho)) +
                 damage[4] * self.upsilon) + sum(self.restoration_costs[idx]))

        print('consequences: ', sum(self.consequences))

        result_matrix_t[0:3, 0] = result_matrix_t[0:3, 1]
        result_matrix[3] = np.sum(result_matrix[0:3, :], axis=0)
        #result_matrix[4:7,0] = result_matrix[4:7,1]
        result_matrix[7] = np.sum(result_matrix[4:7, :], axis=0)
        result_matrix = np.cumsum(result_matrix, axis=1)
        #        result_matrix_id = np.cumsum(result_matrix_id,axis=1)
        # result_rev = np.fliplr(result_matrix_id)
        # result_rev = np.cumsum(result_rev,axis=1)
        # result_matrix_id = np.fliplr(result_rev)

        print('direct:', result_matrix[3, -1])

        print(result_matrix[3, -1] + result_matrix[7, -1])
        # print(result_matrix[7,-1])
        #        print(result_matrix)
        result_matrix[8] = result_matrix[3] + result_matrix[7]

        lines = []
        for i in range(4):
            lines.append(
                '\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(result_matrix.shape[1]):
                lines.append('(' + str(x[j]) + ',' + str(result_matrix[i, j]) +
                             ')')
            lines.append('};')

        for i in range(4, 8):
            xvals = np.arange(0, x[-1] + 0.5, 0.5)
            y = result_matrix[i]
            yinterp = np.interp(xvals, x, y)

            lines.append(
                '\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(xvals.shape[0]):
                lines.append('(' + str(xvals[j]) + ',' + str(yinterp[j]) + ')')
            lines.append('};')

        # TODO: I commented this part to avoid double results *check again for other figures

        # with open(self.filepath + 'tex/costs_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/costs_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        xvals = np.arange(0, x[-1] + 0.5, 0.5)
        dc_vec = np.zeros(xvals.shape[0])
        for i in range(xvals.shape[0]):
            try:
                dc_vec[i] = result_matrix[3, list(x).index(xvals[i])]
            except ValueError:
                pass

        for i in range(dc_vec.shape[0] - 1):
            if dc_vec[i + 1] == 0.0 and dc_vec[i] > 0.0:
                dc_vec[i + 1] = dc_vec[i]

        y = result_matrix[7]
        ic_vec = np.interp(xvals, x, y)

        vecs = [dc_vec, ic_vec, ic_vec + dc_vec]

        lines = []
        for vec in vecs:
            if scenario == '1':
                lines.append(
                    '\\addplot+[const plot, mymark={text}{text mark=1,text mark as node, text mark style={font=\\tiny,circle,inner sep=0pt,fill=myblue!10!white,},}, thick] coordinates {'
                )
            elif scenario == '2':
                lines.append(
                    '\\addplot+[const plot, mymark={text}{text mark=2,text mark as node, text mark style={font=\\tiny,circle,inner sep=0pt,fill=damage2!10!white,},}, thick] coordinates {'
                )
            else:
                lines.append(
                    '\\addplot+[const plot, mymark={text}{text mark=3,text mark as node, text mark style={font=\\tiny,circle,inner sep=0pt,fill=mygreen!10!white,},}, thick] coordinates {'
                )


#            lines.append('\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(vec.shape[0]):
                lines.append('(' + str(xvals[j]) + ',' + str(vec[j]) + ')')
            lines.append('};')

        # TODO: I commented this part to avoid double results *check again for other figures

        # with open(self.filepath + 'tex/sum_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/sum_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        #x = np.append(x,x[-1])
        mat1 = np.append(result_matrix_t[0], result_matrix_t[0][-1])
        # for i in range(len(mat1)-1):
        #     print(mat1[i+1],x[i])

        mat2 = np.append(result_matrix_t[2], result_matrix_t[2][-1])
        # for i in range(len(mat2)-1):
        #     print(mat2[i+1],x[i])

        mat = np.zeros((2, len(mat1) - 1))
        for i in range(len(mat1) - 1):
            mat[0][i] = mat1[i + 1]
            mat[1][i] = mat2[i + 1]

        lines = []
        for i in [0, 1]:
            lines.append(
                '\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(mat.shape[1]):
                lines.append('(' + str(x[j]) + ',' + str(mat[i, j]) + ')')
            lines.append('};')

        # TODO: I commented this part to avoid double results *check again for other figures
        # with open(self.filepath + 'tex/los_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/los_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        pass
示例#6
0
class PpEngine(object):
    """ Postprocessing Simulation Engine
    """
    def __init__(self, filepath='./', bTest=None):

        self.filepath = filepath
        self.test = bTest

        # TODO: What are these I do not think they are needed!
        self.a = 25.5
        self.b = 10
        self.c = 1240

        self.mu = np.array([0.94,
                            0.06])  # % of distribution of cars vs. trucks
        self.xi = np.array([23.02,
                            130.96])  # value of travel for cars vs. trucks
        self.F_w = np.array(
            [6.7, 33]) / 100  # mean fuel consumption for cars vs. trucks
        self.nu = 1.88  # mean fuel price
        self.rho = np.array([
            14.39, 32.54
        ]) / 100  # Operating costs (without fuel) for cars vs. trucks/ 100 km
        self.upsilon = 83.27 * 8  # hourly wage [when lost or delayed trips]* 8 hours/day
        # factor to find the area under the trip distribution curve(average value*9= total trips per day for a zone)
        self.day_factor = 9
        self.gamma = 1  # weight factor for indirect costs

        # self.capacity_losses = {'Bridge': {0: 0, 1: .5, 2: 1, 3: 1}, 'Road': {
        #     0: 0, 1: .7, 2: 1, 3: 1}, 'Tunnel': {0: 0}}
        self.capacity_losses = {}
        data = csv.DictReader(open("capacity_losses.csv", 'r'), delimiter=",")
        for row in data:
            item = self.capacity_losses.get(row["Objects"], dict())
            item[int(row["Damage_Level"])] = float(row["Capacity_Loss"])
            self.capacity_losses[row["Objects"]] = item

        # TODO: Load data from csv file: Done but needs confirmation
        # type 1: normal
        # type 2: emergency
        # type 3: partial
        # self.restoration_names = {0: 'high priority', 1: 'normal', 2: 'low priority'}
        self.restoration_names = {}
        reader = csv.reader(open('./restoration_names.csv'))
        for row in reader:
            self.restoration_names[int(row[0])] = (row[1])

        # self.restoration_types = [0, 1, 2]
        # # self.restoration_types = [2,2,2]
        self.restoration_types = list(
            self.restoration_names.keys())  # TODO: check to make sure

    def initialize_network(self):

        if self.test:
            self.road_graph = read_shp('./test_data/roads.shp')
            self.od_graph = create_od_graph('./test_data/centroids.shp')
            self.con_edges = read_shp('./test_data/connections.shp')
            self.od_matrix = np.genfromtxt('./test_data/od.csv', delimiter=',')
        else:
            self.road_graph = read_shp('./data/roads_clean.shp')
            self.od_graph = create_od_graph('./data/centroids.shp')
            self.con_edges = read_shp('./data/connections.shp')
            self.od_matrix = np.genfromtxt('./data/od.csv', delimiter=',')

        self.graph = create_network_graph(self.road_graph, self.od_graph,
                                          self.con_edges)
        pass

    def initialize_damage(self):
        self.damage = DamageModel(self.graph, self.capacity_losses)
        self.damage.run()
        self.graph_damaged = self.damage.get_graph()
        self.damage_dict = self.damage.get_damage_dict(directed=False)
        pass

    def load_state(self, filename):
        with open(filename, 'r') as f:
            state = ast.literal_eval(f.read())
        return state

    def calculate_damage(self):
        print('--- initialization ---')
        self.initialize_network()
        self.initialize_damage()

        # init_state = self.initialize_state()
        init_state = self.load_state(self.filepath + 'state.txt')

        print('--- no and initial damage ---')
        no_damage = self.run_traffic_model(self.graph, self.od_graph)
        initial_damage = self.run_traffic_model(self.graph_damaged.copy(),
                                                self.od_graph.copy())

        self.damaged = []
        self.damaged.append(get_delta(no_damage, initial_damage))

        print('--- restoration ---')
        self.run_restoration_model(init_state)

        print('--- simulated annealing ---')
        sim_results = Parallel(n_jobs=6)(
            delayed(parallel_model)(graph, self.od_graph, self.od_matrix)
            for graph in self.restoration_graphs[:-1])

        for damaged in sim_results:
            self.damaged.append(get_delta(no_damage, damaged))

        with open(self.filepath + 'damaged.txt', 'w') as f:
            f.write(str(self.damaged))
        pass

    def run_traffic_model(self, graph, od_graph):
        self.traffic = TrafficModel(graph, od_graph, self.od_matrix)
        self.traffic.run()
        # self.traffic.print_results()
        t_k = sum(self.traffic.get_traveltime())
        flow = sum(self.traffic.get_flow())
        hours = sum(self.traffic.get_car_hours())
        distances = sum(self.traffic.get_car_distances())
        lost_trips = sum(self.traffic.get_lost_trips().values())
        # graph_result = self.traffic.get_graph()
        return t_k, flow, hours, distances, lost_trips

    def run_restoration_model(self, sequence=None):
        self.restoration = RestorationModel(self.graph_damaged, self.filepath)
        self.restoration.run(sequence)
        self.restoration_graphs = self.restoration.get_restoration_graphs()
        self.restoration_times = self.restoration.get_restoration_times()
        self.restoration_costs = self.restoration.get_restoration_costs()
        pass

    def load_damage(self, filename):
        with open(filename, 'r') as f:
            damaged = ast.literal_eval(f.read())
        return damaged

    def load_costs(self, filename):
        with open(filename, 'r') as f:
            costs = ast.literal_eval(f.read())
        return costs

    def run(self, scenario):
        print('--- initialization ---')
        self.initialize_network()
        self.initialize_damage()
        init_state = self.load_state(self.filepath + 'state.txt')

        print('--- calculate damage ---')
        if not os.path.isfile(self.filepath + 'damaged.txt'):
            self.calculate_damage()
        else:
            self.damaged = self.load_damage(self.filepath + 'damaged.txt')

        # t_k, flow, hours, distances, lost_trips
        names_dict = {}
        for object in init_state:
            names_dict[object[0]] = get_edge_attribute(
                self.graph, object[0], 'name') + '-' + get_edge_attribute(
                    self.graph, object[0], 'object')[0]

        self.restoration_results = RestorationModel(self.graph_damaged,
                                                    self.filepath)
        # (object,schedule time,needed time,#resources,intervention type, assigned resource)
        sequence_formated = self.restoration_results.format(init_state)

        sort_names = []
        for s in sequence_formated:
            for t in s:
                sort_names.append([
                    t[1] - t[2], t[-1],
                    get_edge_attribute(self.graph, t[0], 'name')[2:]
                ])

        # remove dopples
        seen = set()
        sort_names = [
            x for x in sort_names if x[2] not in seen and not seen.add(x[2])
        ]
        sort_names = sorted(sort_names, key=itemgetter(1))
        sort_names = sorted(sort_names, key=itemgetter(0))

        name_dict = {}
        for name, key in enumerate(sort_names):
            name_dict[key[2]] = str(name + 1)

        print(name_dict)

        #name_dict = {'b-d': '1', ':a-g': '2', 'd-g': '3', 'd-e': '4'}
        # Keys: Object ID , Values: Nr in the table (8) of the paper
        # name_dict = {'1095': '6', '460': '10', '1703': '14', '1237': '20', '562': '11', '2069': '12', '1798': '24', '471': '28', '1371': '29', '1692': '15', '2043': '26', '1802': '8', '1907': '18', '1233': '23',
        #               '1913': '13', '2042': '1', '2052': '7', '2131': '17', '554': '2', '1276': '21', '1202': '22', '1706': '9', '1803': '5', '1905': '19', '1279': '16', '1814': '25', '332': '3', '1498': '27', '461': '4'}

        i = 0
        lines = []

        # TODO : is this  extra? I do not find any other places it is used
        name_list = []
        for s in sequence_formated:
            for t in s:
                name_list.append(
                    get_edge_attribute(self.graph, t[0], 'name')[2:])

        new_name_list = []
        for name in name_list:
            if name not in new_name_list:
                new_name_list.append(name)

        name_list = list(set(name_list))

        program_list = []
        for s in sequence_formated:
            for t in s:
                crew = t[5]
                task_end = t[1]
                task_duration = t[2]
                task_start = task_end - task_duration
                object_type = get_edge_attribute(self.graph, t[0], 'object')
                damage = get_edge_attribute(self.graph, t[0], 'damage')

                condition_state = {1: 'cs1', 2: 'cs2'}
                intervention_type = {
                    10: 'cs1i0',
                    11: 'cs1i1',
                    12: 'cs1i2',
                    20: 'cs2i0',
                    21: 'cs2i1',
                    22: 'cs2i2'
                }
                resources = {1: 'res1', 2: 'res2'}
                x_scale = .4012 / 2
                y_scale = .45
                start_point = (task_start * x_scale, crew * y_scale)
                end_point = (task_end * x_scale, (crew + 1) * y_scale)
                name = get_edge_attribute(self.graph, t[0], 'name')[2:]
                lines.append('\draw[normal,' + resources[t[3]] + ',' +
                             condition_state[damage] + ',' +
                             intervention_type[int(str(damage) + str(t[4]))] +
                             '] ' + str(start_point) + ' rectangle ' +
                             str(end_point) + ' node[mynode,pos=.5] {' +
                             name_dict[name] + ' \\\ ' + object_type[0] + '};')
                #lines.append('\draw[normal,'+resources[t[3]]+','+condition_state[damage]+','+intervention_type[int(str(damage)+str(t[4]))]+'] '+str(start_point)+' rectangle '+str(end_point)+ ' node[mynode,pos=.5] {'+name+' \\\ '+object_type[0]+'};')

                condition_state = {1: '1 minor', 2: '2 major'}
                intervention_type = {
                    10: 'level 1',
                    11: 'level 2',
                    12: 'level 3',
                    20: 'level 1',
                    21: 'level 2',
                    22: 'level 3'
                }
                intervention_nr = {
                    10: 'i',
                    11: 'ii',
                    12: 'iii',
                    20: 'i',
                    21: 'ii',
                    22: 'iii'
                }
                crew_type = {0: 'A', 1: 'B', 2: 'C'}
                sp = ' & '
                nl = '\\'

                program_list.append([
                    int(name_dict[name]), name, object_type,
                    condition_state[damage],
                    intervention_type[int(str(damage) + str(t[4]))],
                    str(task_start / 2),
                    str(task_end / 2),
                    str(task_duration / 2), crew_type[crew]
                ])
                # print(name_dict[name]+sp+name+sp+object_type+sp+condition_state[damage]+sp+intervention_nr[int(str(damage)+str(t[4]))]+sp+intervention_type[int(str(damage)+str(t[4]))]+sp+str(task_start/2)+sp+str(task_end/2)+sp+str(task_duration/2)+sp+crew_type[crew]+sp)
                i += 1

        costs_list = self.load_costs(self.filepath + 'costs.txt')
        for row in costs_list:
            del row[0]

        for i, l in enumerate(program_list):
            a = int(round(costs_list[i][0], 0))
            b = int(round(costs_list[i][1], 0))
            c = int(round(costs_list[i][2], 0))
            d = a + b + c
            l.extend([a, b, c, d])

        seen = set()
        program = [
            x for x in program_list if x[0] not in seen and not seen.add(x[0])
        ]

        sum_fixed = sum(row[-4] for row in program)
        sum_variable = sum(row[-3] for row in program)
        sum_resources = sum(row[-2] for row in program)
        sum_total = sum(row[-1] for row in program)

        program.sort(key=lambda x: x[0])

        program.append([
            '', '', '', '', '', '', '', '', '', sum_fixed, sum_variable,
            sum_resources, sum_total
        ])

        if not os.path.exists(self.filepath + 'tex/'):
            os.makedirs(self.filepath + 'tex/')
            print("Path is created")

        with open(self.filepath + 'tex/program_0' + scenario + '.tex',
                  mode='wt',
                  encoding='utf-8') as f:
            for p in program:
                for i in range(9, 13):
                    p[i] = '\\numprint{' + str(p[i]) + '}'
                f.write(' & '.join(str(e) for e in p) + ' \\\ \n')

        # TODO: I commented this part to avoid double results *check again for other figures
        # with open(self.filepath + 'tex/resources_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/resources_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        #print('t_k, flow, hours, distances, lost_trips')
        # for damage in damaged:
        #     print(damage)
        # TODO: What are these I do not think they are needed!
        fix_costs = [0]
        variable_costs = [0]
        resources_costs = [0]
        all_costs = [0]
        time = [0]

        self.run_restoration_model(init_state)

        #print(self.restoration_costs)

        # print(self.damaged)
        result_matrix = np.zeros((9, len(self.damaged) + 1))
        result_matrix_t = np.zeros((3, len(self.damaged) + 1))
        x = np.zeros(len(self.damaged) + 1)

        self.consequences = []
        for idx, damage in enumerate(self.damaged):
            if idx == 0:
                delta_t = self.restoration_times[idx]
            else:
                delta_t = (self.restoration_times[idx] -
                           self.restoration_times[idx - 1])

            result_matrix[0][idx + 1] = self.restoration_costs[idx][0]
            result_matrix[1][idx + 1] = self.restoration_costs[idx][1]
            result_matrix[2][idx + 1] = self.restoration_costs[idx][2]

            result_matrix[4][idx + 1] = (damage[2] * np.sum(
                self.mu * self.xi)) * delta_t * self.day_factor
            result_matrix[5][idx + 1] = (
                damage[3] * np.sum(self.mu *
                                   (self.nu * self.F_w + self.rho))) * delta_t
            result_matrix[6][idx + 1] = (damage[4] * self.upsilon) * delta_t

            result_matrix_t[0][idx + 1] = damage[2]
            result_matrix_t[1][idx + 1] = damage[3]
            result_matrix_t[2][idx + 1] = damage[4]

            #            print(damage[2], delta_t * (damage[2] * np.sum(self.mu*self.xi)))
            #            print(damage[3], delta_t * (damage[3] * np.sum(self.mu * (self.nu * self.F_w + self.rho))))
            #            print(damage[4], delta_t * (damage[4] * self.upsilon))
            #            print(damage[2])
            x[idx + 1] = self.restoration_times[idx]

            self.consequences.append(
                self.gamma * delta_t *
                (self.day_factor * damage[2] * np.sum(self.mu * self.xi) +
                 damage[3] * np.sum(self.mu *
                                    (self.nu * self.F_w + self.rho)) +
                 damage[4] * self.upsilon) + sum(self.restoration_costs[idx]))

        print('consequences: ', sum(self.consequences))

        result_matrix_t[0:3, 0] = result_matrix_t[0:3, 1]
        result_matrix[3] = np.sum(result_matrix[0:3, :], axis=0)
        #result_matrix[4:7,0] = result_matrix[4:7,1]
        result_matrix[7] = np.sum(result_matrix[4:7, :], axis=0)
        result_matrix = np.cumsum(result_matrix, axis=1)
        #        result_matrix_id = np.cumsum(result_matrix_id,axis=1)
        # result_rev = np.fliplr(result_matrix_id)
        # result_rev = np.cumsum(result_rev,axis=1)
        # result_matrix_id = np.fliplr(result_rev)

        print('direct:', result_matrix[3, -1])

        print(result_matrix[3, -1] + result_matrix[7, -1])
        # print(result_matrix[7,-1])
        #        print(result_matrix)
        result_matrix[8] = result_matrix[3] + result_matrix[7]

        lines = []
        for i in range(4):
            lines.append(
                '\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(result_matrix.shape[1]):
                lines.append('(' + str(x[j]) + ',' + str(result_matrix[i, j]) +
                             ')')
            lines.append('};')

        for i in range(4, 8):
            xvals = np.arange(0, x[-1] + 0.5, 0.5)
            y = result_matrix[i]
            yinterp = np.interp(xvals, x, y)

            lines.append(
                '\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(xvals.shape[0]):
                lines.append('(' + str(xvals[j]) + ',' + str(yinterp[j]) + ')')
            lines.append('};')

        # TODO: I commented this part to avoid double results *check again for other figures

        # with open(self.filepath + 'tex/costs_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/costs_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        xvals = np.arange(0, x[-1] + 0.5, 0.5)
        dc_vec = np.zeros(xvals.shape[0])
        for i in range(xvals.shape[0]):
            try:
                dc_vec[i] = result_matrix[3, list(x).index(xvals[i])]
            except ValueError:
                pass

        for i in range(dc_vec.shape[0] - 1):
            if dc_vec[i + 1] == 0.0 and dc_vec[i] > 0.0:
                dc_vec[i + 1] = dc_vec[i]

        y = result_matrix[7]
        ic_vec = np.interp(xvals, x, y)

        vecs = [dc_vec, ic_vec, ic_vec + dc_vec]

        lines = []
        for vec in vecs:
            if scenario == '1':
                lines.append(
                    '\\addplot+[const plot, mymark={text}{text mark=1,text mark as node, text mark style={font=\\tiny,circle,inner sep=0pt,fill=myblue!10!white,},}, thick] coordinates {'
                )
            elif scenario == '2':
                lines.append(
                    '\\addplot+[const plot, mymark={text}{text mark=2,text mark as node, text mark style={font=\\tiny,circle,inner sep=0pt,fill=damage2!10!white,},}, thick] coordinates {'
                )
            else:
                lines.append(
                    '\\addplot+[const plot, mymark={text}{text mark=3,text mark as node, text mark style={font=\\tiny,circle,inner sep=0pt,fill=mygreen!10!white,},}, thick] coordinates {'
                )


#            lines.append('\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(vec.shape[0]):
                lines.append('(' + str(xvals[j]) + ',' + str(vec[j]) + ')')
            lines.append('};')

        # TODO: I commented this part to avoid double results *check again for other figures

        # with open(self.filepath + 'tex/sum_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/sum_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        #x = np.append(x,x[-1])
        mat1 = np.append(result_matrix_t[0], result_matrix_t[0][-1])
        # for i in range(len(mat1)-1):
        #     print(mat1[i+1],x[i])

        mat2 = np.append(result_matrix_t[2], result_matrix_t[2][-1])
        # for i in range(len(mat2)-1):
        #     print(mat2[i+1],x[i])

        mat = np.zeros((2, len(mat1) - 1))
        for i in range(len(mat1) - 1):
            mat[0][i] = mat1[i + 1]
            mat[1][i] = mat2[i + 1]

        lines = []
        for i in [0, 1]:
            lines.append(
                '\\addplot+[const plot, no marks, thick] coordinates {')
            for j in range(mat.shape[1]):
                lines.append('(' + str(x[j]) + ',' + str(mat[i, j]) + ')')
            lines.append('};')

        # TODO: I commented this part to avoid double results *check again for other figures
        # with open(self.filepath + 'tex/los_0'+scenario+'.tex', mode='wt', encoding='utf-8') as myfile:
        #     myfile.write('\n'.join(lines))

        with open(self.filepath + 'tex/los_01.tex',
                  mode='wt',
                  encoding='utf-8') as myfile:
            myfile.write('\n'.join(lines))

        pass
示例#7
0
class Engine(object):
    """
    Simulation engine class:
    This Engine is used to find the near optimal restoration programs for transportation networks.

    Needed input Data
    ----------

        csv file for restoration names (levels)
        csv file for capacity losses of objects with respect to each damage level.
        csv file containing the od matrix
        shape files containing the object IDs and their related length, width (determined from the object class),
        flow direction (one way: true or false), capacity, speed limit and damage level.

    Parameters
    ----------
        self.test : bool
            a variable to define if the model runs on test data or original data.

        self.capacity_losses : Nested dict
            This attribute defines the different level of capacity losses and the related percentage of capacity loss
            for different objects. The data is imported from a csv file.
            In this example, the objects 'Bridge' , 'Road', and 'Tunnel' are the keys; the nested keys refer to the
            capacity loss levels 0, 1 and 2 and the values relate to the percentage of capacity loss
            (e.g 0 , 50% and 100% for bridges).

            self.capacity_losses = {'Bridge': {0: 0, 1: .5, 2: 1}, 'Road': {0: 0, 1: .7, 2: 1}, 'Tunnel': {0: 0}}

        self.restoration_names : dict
            This attribute shows the different levels for restoration programs. The data is imported from a csv file
            In this example :
            self.restoration_names = {0: 'high priority', 1: 'normal', 2: 'low priority'}

        self.restoration_types:  list
            A list of the the keys in the self.restoration_names referring to the intervention level

        self.restoration_constraint : bool
            It shows whether we have constraints in the restoration scenarios or not.

        self.output_directory: directory path
            It shows where the output is going to be saved.

    Methods
    -------
        __init__:
            This is the constructor function of the engine class

        initialize_network:
            This function will initialize the network and will creat the network graph (self.graph) using the
            information in the GIS .shp files and the csv file that contains the od matrix.

        initialize_damage:
            Runs the DamageModel class on the "damage" object and creates the damage dictionary (self.damage_dict)

        initialize_state:
            This function randomly selects objects and is used as an input to the SimAnnealInterface.

        run_traffic_model:
            Runs the TrafficModel class and "traffic" object and gets the travel time (t_k), flow, car hours and
            distances, along with the lost trips.

        run:
            This function is used to run the Engine class (optimization of the restoration programs) on the object named
            model that was constructed from the Engine class.
    """
    def __init__(self,
                 output_directory='./',
                 bTest=None,
                 bRestConstraint=None):
        """
        This is the constructor function of the engine class
        
        Input parameters
        ----------
            output_directory: directory path
                It shows where the output is going to be saved.
                
            bTest : bool
                a variable to define if the model runs on test data or original data.
                
            bRestConstraint : bool
                It shows whether we have constraints in the restoration scenarios or not.
        """
        self.test = bTest

        self.capacity_losses = {}
        data = csv.DictReader(open("capacity_losses.csv", 'r'), delimiter=",")
        for row in data:
            item = self.capacity_losses.get(row["Objects"], dict())
            item[int(row["Damage_Level"])] = float(row["Capacity_Loss"])
            self.capacity_losses[row["Objects"]] = item

        self.restoration_names = {}
        reader = csv.reader(open('./restoration_names.csv'))
        for row in reader:
            self.restoration_names[int(row[0])] = (row[1])

        self.restoration_types = list(
            self.restoration_names.keys())  #TODO: check to make sure
        self.restoration_constraint = bRestConstraint
        self.output_directory = output_directory
        if not os.path.exists(output_directory):
            os.makedirs(output_directory)

    def initialize_network(self):
        """
        This function will initialize the network and will creat the network graph (self.graph) using the information
        in the GIS .shp files and the csv file that contains the od matrix.
        If the test is true the function will use the test data while when test is false the function will run on the
        actual data. The output of the function is the network graph.

        Input data:
        shape file (.shp) for the roads, centroids and connections.
        csv file containing the od matrix
        """

        if self.test:
            self.road_graph = read_shp('./test_data/roads.shp')
            self.od_graph = create_od_graph('./test_data/centroids.shp')
            self.con_edges = read_shp('./test_data/connections.shp')
            self.od_matrix = np.genfromtxt('./test_data/od.csv', delimiter=',')
        else:
            self.road_graph = read_shp('./data/roads_clean.shp')
            self.od_graph = create_od_graph('./data/centroids.shp')
            self.con_edges = read_shp('./data/connections.shp')
            self.od_matrix = np.genfromtxt('./data/od.csv', delimiter=',')

        self.graph = create_network_graph(self.road_graph, self.od_graph,
                                          self.con_edges)

        pass

    def initialize_damage(self):
        """
         Runs the DamageModel class on "damage" object and creates the damage dictionary (self.damage_dict)
            TODO: Define whether get_damage_dict is directed or not, meaning ...and some elaboration on the process,
            Does this refer to directed nodes for edges?

        Input parameters:
        ----------
            self.graph: DiGraph
                A  directed graph constructed using the create_network_graph () method in initialize network
                method.

            self.capacity_losses: Nested dict
                This attribute defines the different level of capacity losses and the related percentage of capacity loss
                for different objects. The data is imported from a csv file.
        """

        self.damage = DamageModel(self.graph, self.capacity_losses)
        self.damage.run()
        self.graph_damaged = self.damage.get_graph()
        self.damage_dict = self.damage.get_damage_dict(directed=False)
        pass

    def initialize_state(self):
        """
        This function randomly selects objects and returns init_state (to be used as an input to the SimAnnealInterface.)
        """

        init_edges = list(
            self.damage_dict.keys())  # gets the edges of damaged objects
        random.shuffle(init_edges)

        init_state = []
        for edge in init_edges:
            if self.restoration_constraint:  # TODO we are assigning high priority restoration to all damaged edges ? why?
                init_state.append((edge, 0))
            else:
                init_state.append(
                    (edge, random.choice(self.restoration_types)))
        return init_state

    def run_traffic_model(self, graph, od_graph):
        """
        Runs the TrafficModel class on "traffic" object and gets the travel time (t_k), flow, car hours and distances,
        along with the values for lost trips dict.
        """

        self.traffic = TrafficModel(graph, od_graph, self.od_matrix)
        self.traffic.run()
        t_k = sum(self.traffic.get_traveltime())
        flow = sum(self.traffic.get_flow())
        hours = sum(self.traffic.get_car_hours())
        distances = sum(self.traffic.get_car_distances())
        lost_trips = sum(self.traffic.get_lost_trips().values())
        return t_k, flow, hours, distances, lost_trips

    def run(self):
        """
        This function is used to run the Engine class (optimization of the restoration programs) on the object
        that was constructed from the Engine class.

        This is the main function of the Engine class that includes the following methods, and classes:

            methods:
            -------
                initialize_network
                initialize_damage
                initialize_state
                run_traffic_model
                anneal

        Class:
        SimAnnealInterface(init_state, self.graph, self.od_graph,self.od_matrix, self.graph_damaged, damage,
        self.output_directory)
        TODO: write more info here for SA

        """
        self.initialize_network()
        self.initialize_damage()
        init_state = self.initialize_state()

        # getting t_k, flow, hours, distances, lost_trips by running the traffic model before damage
        no_damage = self.run_traffic_model(self.graph, self.od_graph)

        # getting t_k, flow, hours, distances, lost_trips by running the traffic model after damage
        initial_damage = self.run_traffic_model(self.graph_damaged.copy(),
                                                self.od_graph.copy())

        damage = [no_damage, initial_damage]

        optimize = SimAnnealInterface(init_state, self.graph, self.od_graph,
                                      self.od_matrix, self.graph_damaged,
                                      damage, self.output_directory)

        optimize.copy_strategy = "slice"

        state, e = optimize.anneal(
        )  # Minimizes the energy of a system by simulated annealing

        print("consequences: %i" % e)

        self.restoration_results = RestorationModel(self.graph_damaged)

        # (object,schedule time (when it's finished),needed time,# of resources,intervention type, assignd resource)
        sequence_formated = self.restoration_results.format(state)

        with open(self.output_directory + 'state.txt', 'w') as f:
            f.write(str(state))

        with open(self.output_directory + 'state_formated.txt', 'w') as f:
            f.write(str(sequence_formated))
        pass
示例#8
0
class Engine(object):
    """ Simulation engine
    """
    def __init__(self, output_directory='./'):
        self.capacity_losses = {
            'Bridge': {
                0: 0,
                1: .5,
                2: 1,
                3: 1
            },
            'Road': {
                0: 0,
                1: .7,
                2: 1,
                3: 1
            },
            'Tunnel': {
                0: 0
            }
        }

        # TODO: Load data from csv file
        self.restoration_types = [0, 1, 2]

        self.restoration_constraint = False
        self.output_directory = output_directory

    def initialize_network(self):
        self.road_graph = read_shp('./data/roads.shp')
        self.od_graph = create_od_graph('./data/centroids.shp')
        self.con_edges = read_shp('./data/connections.shp')
        self.od_matrix = np.genfromtxt('./data/od.csv', delimiter=',')

        self.graph = create_network_graph(self.road_graph, self.od_graph,
                                          self.con_edges)
        pass

    def initialize_damage(self):
        self.damage = DamageModel(self.graph, self.capacity_losses)
        self.damage.run()
        self.graph_damaged = self.damage.get_graph()
        self.damage_dict = self.damage.get_damage_dict(directed=False)
        #self.damage_dict = self.damage.get_damage_dict(directed=True)
        pass

    def run_restoration_model(self, sequence=None):
        self.restoration = RestorationModel(self.graph_damaged)
        self.restoration.run(sequence)
        self.restoration_graphs = self.restoration.get_restoration_graphs()
        self.restoration_times = self.restoration.get_restoration_times()
        self.restoration_costs = self.restoration.get_restoration_costs()
        pass

    def run_traffic_model(self, graph, od_graph):
        # set up traffic model
        self.traffic = TrafficAssignment(graph, od_graph, self.od_matrix)
        # run traffic simulation
        self.traffic.run()
        t_k = sum(self.traffic.get_traveltime())
        flow = sum(self.traffic.get_flow())
        hours = sum(self.traffic.get_car_hours())
        distances = sum(self.traffic.get_car_distances())
        lost_trips = sum(self.traffic.get_lost_trips().values())
        return t_k, flow, hours, distances, lost_trips

    def initialize_state(self):
        init_edges = list(self.damage_dict.keys())
        random.shuffle(init_edges)

        init_state = []

        for edge in init_edges:
            if self.restoration_constraint:
                init_state.append((edge, 0))
            else:
                init_state.append(
                    (edge, random.choice(self.restoration_types)))
        return init_state

    def load_state(self, filename):
        with open(filename, 'r') as f:
            state = ast.literal_eval(f.read())
        return state

    def load_damage(self, filename):
        with open(filename, 'r') as f:
            damaged = ast.literal_eval(f.read())
        return damaged

    def run(self):
        self.initialize_network()
        self.initialize_damage()
        init_state = self.initialize_state()

        no_damage = self.run_traffic_model(self.graph, self.od_graph)
        initial_damage = self.run_traffic_model(self.graph_damaged.copy(),
                                                self.od_graph.copy())

        damage = [no_damage, initial_damage]

        optimize = SimAnnealer(init_state, self.graph, self.od_graph,
                               self.od_matrix, self.graph_damaged, damage,
                               self.output_directory)

        optimize.copy_strategy = "slice"

        state, e = optimize.anneal()

        print("consequences: %i" % e)

        self.restoration_results = RestorationModel(self.graph_damaged)
        # (object,schedule time,needed time,#resources,intervention type, assignd resource)
        sequence_formated = self.restoration_results.format(state)

        with open(self.output_directory + 'state.txt', 'w') as f:
            f.write(str(state))

        with open(self.output_directory + 'state_formated.txt', 'w') as f:
            f.write(str(sequence_formated))
        pass