def petrinetcreator(self, places, transitions, arcs):
        net = PetriNet("new_petri_net")

        source = PetriNet.Place("source")
        sink = PetriNet.Place("sink")
        for i in range(1, places + 1):
            p = PetriNet.Place("p_" + str(i))
            net.places.add(p)
        net.places.add(source)
        net.places.add(sink)

        for i in range(1, transitions + 1):
            t = PetriNet.Transition("name_" + str(i), "label_" + str(i))
            net.transitions.add(t)

        for i in range(1, len(arcs + 1)):
            arc = arcs[i].split()
            utils.add_arc_from_to(arc[0], arc[1], net)

        initial_marking = Marking()
        initial_marking[source] = 1
        final_marking = Marking()
        final_marking[sink] = 1

        return net
示例#2
0
def apply(log, net, initial_marking, final_marking, parameters=None):
    """
    Method to apply token-based replay

    Parameters
    -----------
    log
        Log
    net
        Petri net
    initial_marking
        Initial marking
    final_marking
        Final marking
    parameters
        Parameters of the algorithm
    """
    if parameters is None:
        parameters = {}

    for t in net.transitions:
        ma = Marking()
        for a in t.out_arcs:
            p = a.target
            ma[p] = a.weight
        t.out_marking = ma

    for t in net.transitions:
        ma = Marking()
        for a in t.in_arcs:
            p = a.source
            ma[p] = a.weight
        t.in_marking = ma

    variants_idxs = variants_filter.get_variants_from_log_trace_idx(log, parameters=parameters)
    results = []

    tmap = {}
    bmap = {}
    for t in net.transitions:
        if t.label is not None:
            if t.label not in tmap:
                tmap[t.label] = []
            tmap[t.label].append(t)

    for variant in variants_idxs:
        vlist = variant.split(",")
        result = tr_vlist(vlist, net, initial_marking, final_marking, tmap, bmap, parameters=parameters)
        results.append(result)

    al_idx = {}
    for index_variant, variant in enumerate(variants_idxs):
        for trace_idx in variants_idxs[variant]:
            al_idx[trace_idx] = results[index_variant]

    ret = []
    for i in range(len(log)):
        ret.append(al_idx[i])

    return ret
示例#3
0
def to(net0, im0, fm0):
    net = PetriNet("")
    im = Marking()
    fm = Marking()
    dp = {}
    dt = {}
    i = 0
    while i < len(net0[0]):
        p = PetriNet.Place(str(net0[0][i]))
        net.places.add(p)
        dp[i] = p
        i = i + 1
    i = 0
    while i < len(net0[1]):
        t = PetriNet.Transition("t%d" % (i), net0[1][i][0])
        net.transitions.add(t)
        dt[i] = t
        i = i + 1
    i = 0
    while i < len(net0[1]):
        for p in net0[1][i][1]:
            petri_utils.utils.add_arc_from_to(dp[p], dt[i], net)
        for p in net0[1][i][2]:
            petri_utils.utils.add_arc_from_to(dt[i], dp[p], net)
        i = i + 1
    for p in im0:
        im[dp[p]] = im0[p]
    for p in fm0:
        fm[dp[p]] = fm0[p]
    return net, im, fm
示例#4
0
def construct_trace_net(trace,
                        trace_name_key=xes_util.DEFAULT_NAME_KEY,
                        activity_key=xes_util.DEFAULT_NAME_KEY):
    """
    Creates a trace net, i.e. a trace in Petri net form.

    Parameters
    ----------
    trace: :class:`list` input trace, assumed to be a list of events
    trace_name_key: :class:`str` key of the attribute that defines the name of the trace
    activity_key: :class:`str` key of the attribute of the events that defines the activity name

    Returns
    -------
    tuple: :class:`tuple` of the net, initial marking and the final marking

    """
    net = PetriNet('trace net of %s' %
                   trace.attributes[trace_name_key] if trace_name_key in
                   trace.attributes else ' ')
    place_map = {0: PetriNet.Place('p_0')}
    net.places.add(place_map[0])
    for i in range(0, len(trace)):
        t = PetriNet.Transition('t_' + trace[i][activity_key] + '_' + str(i),
                                trace[i][activity_key])
        net.transitions.add(t)
        place_map[i + 1] = PetriNet.Place('p_' + str(i + 1))
        net.places.add(place_map[i + 1])
        add_arc_from_to(place_map[i], t, net)
        add_arc_from_to(t, place_map[i + 1], net)
    return net, Marking({place_map[0]: 1}), Marking({place_map[len(trace)]: 1})
示例#5
0
def merge_comp(comp1, comp2):
    net = PetriNet("")
    im = Marking()
    fm = Marking()
    places = {}
    trans = {}

    for pl in comp1[0].places:
        places[pl.name] = PetriNet.Place(pl.name)
        net.places.add(places[pl.name])
        if pl in comp1[1]:
            im[places[pl.name]] = comp1[1][pl]
        if pl in comp1[2]:
            fm[places[pl.name]] = comp1[2][pl]

    for pl in comp2[0].places:
        places[pl.name] = PetriNet.Place(pl.name)
        net.places.add(places[pl.name])
        if pl in comp2[1]:
            im[places[pl.name]] = comp2[1][pl]
        if pl in comp2[2]:
            fm[places[pl.name]] = comp2[2][pl]

    for tr in comp1[0].transitions:
        trans[tr.name] = PetriNet.Transition(tr.name, tr.label)
        net.transitions.add(trans[tr.name])

    for tr in comp2[0].transitions:
        if not tr.name in trans:
            trans[tr.name] = PetriNet.Transition(tr.name, tr.label)
            net.transitions.add(trans[tr.name])

    for arc in comp1[0].arcs:
        if type(arc.source) is PetriNet.Place:
            add_arc_from_to(places[arc.source.name], trans[arc.target.name],
                            net)
        else:
            add_arc_from_to(trans[arc.source.name], places[arc.target.name],
                            net)

    for arc in comp2[0].arcs:
        if type(arc.source) is PetriNet.Place:
            add_arc_from_to(places[arc.source.name], trans[arc.target.name],
                            net)
        else:
            add_arc_from_to(trans[arc.source.name], places[arc.target.name],
                            net)

    lvis_labels = sorted(
        [t.label for t in net.transitions if t.label is not None])
    t_tuple = tuple(
        sorted(
            list(
                int(hashlib.md5(t.name.encode('utf-8')).hexdigest(), 16)
                for t in net.transitions)))
    net.lvis_labels = lvis_labels
    net.t_tuple = t_tuple

    return (net, im, fm)
示例#6
0
 def test_figure415(self):
     net = PetriNet("figure_4_15")
     p_1 = PetriNet.Place("p_1")
     p_2 = PetriNet.Place("p_2")
     p_3 = PetriNet.Place("p_3")
     p_4 = PetriNet.Place("p_4")
     p_5 = PetriNet.Place("p_5")
     p_6 = PetriNet.Place("p_6")
     p_7 = PetriNet.Place("p_7")
     net.places.add(p_1)
     net.places.add(p_2)
     net.places.add(p_3)
     net.places.add(p_4)
     net.places.add(p_5)
     net.places.add(p_6)
     net.places.add(p_7)
     t_1 = PetriNet.Transition("t_1", "t_1")
     t_2 = PetriNet.Transition("t_2", "t_2")
     t_3 = PetriNet.Transition("t_3", "t_3")
     t_4 = PetriNet.Transition("t_4", "t_4")
     t_5 = PetriNet.Transition("t_5", "t_5")
     t_6 = PetriNet.Transition("t_6", "t_6")
     net.transitions.add(t_1)
     net.transitions.add(t_2)
     net.transitions.add(t_3)
     net.transitions.add(t_4)
     net.transitions.add(t_5)
     net.transitions.add(t_6)
     utils.add_arc_from_to(p_1, t_1, net)
     utils.add_arc_from_to(t_1, p_3, net)
     utils.add_arc_from_to(t_1, p_2, net)
     utils.add_arc_from_to(t_1, p_5, net)
     utils.add_arc_from_to(p_5, t_2, net)
     utils.add_arc_from_to(p_5, t_5, net)
     utils.add_arc_from_to(p_3, t_2, net)
     utils.add_arc_from_to(p_3, t_4, net)
     utils.add_arc_from_to(t_2, p_6, net)
     utils.add_arc_from_to(t_2, p_4, net)
     utils.add_arc_from_to(t_5, p_5, net)
     utils.add_arc_from_to(t_5, p_3, net)
     utils.add_arc_from_to(p_2, t_2, net)
     utils.add_arc_from_to(t_3, p_2, net)
     utils.add_arc_from_to(t_3, p_3, net)
     utils.add_arc_from_to(t_3, p_4, net)
     utils.add_arc_from_to(p_6, t_5, net)
     utils.add_arc_from_to(p_6, t_6, net)
     utils.add_arc_from_to(p_6, t_3, net)
     utils.add_arc_from_to(t_4, p_6, net)
     utils.add_arc_from_to(t_4, p_5, net)
     utils.add_arc_from_to(p_4, t_3, net)
     utils.add_arc_from_to(p_4, t_6, net)
     utils.add_arc_from_to(p_4, t_4, net)
     utils.add_arc_from_to(t_6, p_7, net)
     initial_marking = Marking()
     initial_marking[p_1] = 1
     final_marking = Marking()
     final_marking[p_7] = 1
     self.assertTrue(woflan.apply(net, initial_marking, final_marking))
示例#7
0
def test_marking_equality():
    net = PetriNet()

    p0 = PetriNet.Place('p0')
    p1 = PetriNet.Place('p1')
    net.places.update([p0, p1])

    m0 = Marking([p0])
    m1 = Marking([p0])

    assert m0 == m1
示例#8
0
def construct(pn1, im1, fm1, pn2, im2, fm2, skip):
    """
    Constructs the synchronous product net of two given Petri nets.


    :param pn1: Petri net 1
    :param im1: Initial marking of Petri net 1
    :param fm1: Final marking of Petri net 1
    :param pn2: Petri net 2
    :param im2: Initial marking of Petri net 2
    :param fm2: Final marking of Petri net 2
    :param skip: Symbol to be used as skip

    Returns
    -------
    :return: Synchronous product net and associated marking labels are of the form (a,>>)
    """
    sync_net = PetriNet('synchronous_product_net of %s and %s' %
                        (pn1.name, pn2.name))
    t1_map, p1_map = __copy_into(pn1, sync_net, True, skip)
    t2_map, p2_map = __copy_into(pn2, sync_net, False, skip)

    for t1 in pn1.transitions:
        for t2 in pn2.transitions:
            if t1.label == t2.label:
                sync = PetriNet.Transition((t1.name, t2.name),
                                           (t1.label, t2.label))
                sync_net.transitions.add(sync)
                for a in t1.in_arcs:
                    add_arc_from_to(p1_map[a.source], sync, sync_net)
                for a in t2.in_arcs:
                    add_arc_from_to(p2_map[a.source], sync, sync_net)
                for a in t1.out_arcs:
                    add_arc_from_to(sync, p1_map[a.target], sync_net)
                for a in t2.out_arcs:
                    add_arc_from_to(sync, p2_map[a.target], sync_net)

    sync_im = Marking()
    sync_fm = Marking()
    for p in im1:
        sync_im[p1_map[p]] = im1[p]
    for p in im2:
        sync_im[p2_map[p]] = im2[p]
    for p in fm1:
        sync_fm[p1_map[p]] = fm1[p]
    for p in fm2:
        sync_fm[p2_map[p]] = fm2[p]

    # update 06/02/2021: to distinguish the sync nets that are output of this method, put a property in the sync net
    sync_net.properties[properties.IS_SYNC_NET] = True

    return sync_net, sync_im, sync_fm
示例#9
0
    def test_52(self):
        # creating an empty Petri net
        from pm4py.objects.petri.petrinet import PetriNet, Marking
        net = PetriNet("new_petri_net")

        # creating source, p_1 and sink place
        source = PetriNet.Place("source")
        sink = PetriNet.Place("sink")
        p_1 = PetriNet.Place("p_1")
        # add the places to the Petri Net
        net.places.add(source)
        net.places.add(sink)
        net.places.add(p_1)

        # Create transitions
        t_1 = PetriNet.Transition("name_1", "label_1")
        t_2 = PetriNet.Transition("name_2", "label_2")
        # Add the transitions to the Petri Net
        net.transitions.add(t_1)
        net.transitions.add(t_2)

        # Add arcs
        from pm4py.objects.petri import utils
        utils.add_arc_from_to(source, t_1, net)
        utils.add_arc_from_to(t_1, p_1, net)
        utils.add_arc_from_to(p_1, t_2, net)
        utils.add_arc_from_to(t_2, sink, net)

        # Adding tokens
        initial_marking = Marking()
        initial_marking[source] = 1
        final_marking = Marking()
        final_marking[sink] = 1

        from pm4py.objects.petri.exporter import exporter as pnml_exporter
        pnml_exporter.apply(net, initial_marking, "createdPetriNet1.pnml", final_marking=final_marking)

        from pm4py.visualization.petrinet import visualizer as pn_visualizer
        gviz = pn_visualizer.apply(net, initial_marking, final_marking)

        from pm4py.visualization.petrinet import visualizer as pn_visualizer
        parameters = {pn_visualizer.Variants.WO_DECORATION.value.Parameters.FORMAT: "svg"}
        gviz = pn_visualizer.apply(net, initial_marking, final_marking, parameters=parameters)

        from pm4py.visualization.petrinet import visualizer as pn_visualizer
        parameters = {pn_visualizer.Variants.WO_DECORATION.value.Parameters.FORMAT: "svg"}
        gviz = pn_visualizer.apply(net, initial_marking, final_marking, parameters=parameters)
        pn_visualizer.save(gviz, "alpha.svg")

        os.remove("createdPetriNet1.pnml")
        os.remove("alpha.svg")
示例#10
0
def project_net_on_place(place):
    """
    Project a Petri net on a place

    Parameters
    -------------
    place
        Place

    Returns
    -------------
    net
        (Place) net
    im
        Empty initial marking
    fm
        Empty final marking
    """
    place_net = PetriNet()
    place_net_im = Marking()
    place_net_fm = Marking()

    input_trans = [arc.source for arc in place.in_arcs]
    output_trans = [arc.target for arc in place.out_arcs]

    if len(input_trans) == 0 or len(output_trans) == 0:
        raise Exception("place projection not available on source/sink places")

    input_trans_visible = [trans for trans in input_trans if trans.label]
    output_trans_visible = [trans for trans in output_trans if trans.label]

    if not len(input_trans) == len(input_trans_visible) or not len(
            output_trans) == len(output_trans_visible):
        raise Exception(
            "place projection not available on places that have invisible transitions as preset/postset"
        )

    new_place = PetriNet.Place(place.name)
    place_net.places.add(new_place)

    for trans in input_trans:
        new_trans = PetriNet.Transition(trans.name, trans.label)
        place_net.transitions.add(new_trans)
        add_arc_from_to(new_trans, new_place, place_net)

    for trans in output_trans:
        new_trans = PetriNet.Transition(trans.name, trans.label)
        place_net.transitions.add(new_trans)
        add_arc_from_to(new_place, new_trans, place_net)

    return place_net, place_net_im, place_net_fm
示例#11
0
    def __init__(self,
                 current_time: datetime,
                 decay_values: dict,
                 token_counts: dict,
                 marking: Marking,
                 place_list: list,
                 resource_count: dict = None,
                 resource_indices: dict = None,
                 loadExisting: bool = False):
        self.__data__ = {"ct": current_time}
        #ct = current time

        if not loadExisting:
            decay_vector = []
            token_count_vector = []
            marking_vector = []

            for place in place_list:
                decay_vector.append(decay_values[str(place)])
                token_count_vector.append(token_counts[str(place)])

                if str(place) in [str(key) for key in marking.keys()]:
                    for key, val in marking.items():
                        if str(key) == str(place):
                            marking_vector.append(val)
                            break
                else:
                    marking_vector.append(0)

            if resource_count is None:
                self.__data__["tss"] = [
                    decay_vector, token_count_vector, marking_vector
                ]
            else:
                resource_vector = [
                    0 for _ in range(len(resource_indices.keys()))
                ]
                for key in resource_count.keys():
                    resource_vector[
                        resource_indices[key]] = resource_count[key]
                self.__data__["tss"] = [
                    decay_vector, token_count_vector, marking_vector,
                    resource_vector
                ]
        else:
            """ Load from File """
            self.__data__ = {
                "ct": current_time,
                "tss": [decay_values, token_counts, marking]
            }
示例#12
0
文件: amstc.py 项目: BoltMaud/da4py
 def __copy_net(self, pn, m0, mf):
     self.__pn = deepcopy(pn)
     self.__transitions = list(self.__pn.transitions)
     self.__places = list(self.__pn.places)
     self.__arcs = list(self.__pn.arcs)
     self.__m0 = Marking()
     self.__mf = Marking()
     for p in self.__pn.places:
         for n in m0.keys():
             if n.name == p.name:
                 self.__m0[p] = 1
         for n in mf.keys():
             if n.name == p.name:
                 self.__mf[p] = 1
示例#13
0
def remove_initial_hidden_if_possible(net, im):
    """
    Remove initial hidden transition if possible

    Parameters
    ------------
    net
        Petri net
    im
        Initial marking

    Returns
    ------------
    net
        Petri net
    im
        Possibly different initial marking
    """
    source = list(im.keys())[0]
    first_hidden = list(source.out_arcs)[0].target
    target_places_first_hidden = [x.target for x in first_hidden.out_arcs]
    if len(target_places_first_hidden) == 1:
        target_place_first_hidden = target_places_first_hidden[0]
        if len(target_place_first_hidden.in_arcs) == 1:
            new_im = Marking()
            new_im[target_place_first_hidden] = 1
            petri.utils.remove_place(net, source)
            petri.utils.remove_transition(net, first_hidden)
            return net, new_im
    return net, im
示例#14
0
def log_to_Pn(traces_xes,size_of_run):
    traces = project_traces(traces_xes)
    petri_of_traces=PetriNet()
    init, end=PetriNet.Place("init"),PetriNet.Place("end")
    [petri_of_traces.places.add(place) for place in [init, end]]
    prec=init
    for t in traces:
        prec=init
        for a in range (0,min(size_of_run,len(t))):
            transition=PetriNet.Transition(t[a]+str(a), t[a])
            petri_of_traces.transitions.add(transition)
            place_suiv=end if a in [size_of_run-1,len(t)-1]  else PetriNet.Place(t[a]+str(a))
            add_arc_from_to(transition, place_suiv, petri_of_traces)
            add_arc_from_to(prec, transition, petri_of_traces)
            prec=place_suiv
    m0=Marking().__add__({init:1})
    mf=Marking().__add__({end:1})
    return petri_of_traces,m0,mf
示例#15
0
def add_markings(curr, add):
    m = Marking()
    for p in curr.items():
        m[p[0]] = p[1]
    for p in add.items():
        m[p[0]] += p[1]
        if m[p[0]] == 0:
            del m[p[0]]
    return m
def get_marking(net):
    """
    Helper functions that creates a pm4py Marking object from a pm4py PetriNet
    where the marking is encoded in the properties.
    """
    marking = Marking()
    for place in net.places:
        marking[place] = place.properties['tokens']
    return marking
示例#17
0
def get_strongly_connected_subnets(net):
    """
    Get the strongly connected components subnets in the Petri net

    Parameters
    -------------
    net
        Petri net

    Returns
    -------------
    strongly_connected_transitions
        List of strongly connected transitions of the Petri net
    """
    import networkx as nx

    graph, inv_dictionary = create_networkx_directed_graph(net)
    sccg = list(nx.strongly_connected_components(graph))
    strongly_connected_subnets = []
    for sg in list(sccg):
        if len(sg) > 1:
            subnet = PetriNet()
            imarking = Marking()
            fmarking = Marking()
            corr = {}
            for node in sg:
                if node in inv_dictionary:
                    if type(inv_dictionary[node]) is PetriNet.Transition:
                        prev_trans = inv_dictionary[node]
                        new_trans = PetriNet.Transition(
                            prev_trans.name, prev_trans.label)
                        corr[node] = new_trans
                        subnet.transitions.add(new_trans)
                    if type(inv_dictionary[node]) is PetriNet.Place:
                        prev_place = inv_dictionary[node]
                        new_place = PetriNet.Place(prev_place.name)
                        corr[node] = new_place
                        subnet.places.add(new_place)
            for edge in graph.edges:
                if edge[0] in sg and edge[1] in sg:
                    add_arc_from_to(corr[edge[0]], corr[edge[1]], subnet)
            strongly_connected_subnets.append([subnet, imarking, fmarking])

    return strongly_connected_subnets
示例#18
0
def align_fake_log_stop_marking(fake_log, net, marking, final_marking, parameters=None):
    """
    Align the 'fake' log_skeleton with all the prefixes in order to get the markings in which
    the alignment stops

    Parameters
    -------------
    fake_log
        Fake log_skeleton
    net
        Petri net
    marking
        Marking
    final_marking
        Final marking
    parameters
        Parameters of the algorithm

    Returns
    -------------
    alignment
        For each trace in the log_skeleton, return the marking in which the alignment stops (expressed as place name with count)
    """
    if parameters is None:
        parameters = {}
    align_result = []
    for i in range(len(fake_log)):
        trace = fake_log[i]
        sync_net, sync_initial_marking, sync_final_marking = build_sync_net(trace, net, marking, final_marking,
                                                                            parameters=parameters)
        stop_marking = Marking()
        for pl, count in sync_final_marking.items():
            if pl.name[1] == utils.SKIP:
                stop_marking[pl] = count
        cost_function = utils.construct_standard_cost_function(sync_net, utils.SKIP)

        # perform the alignment of the prefix
        res = precision_utils.__search(sync_net, sync_initial_marking, sync_final_marking, stop_marking, cost_function,
                                       utils.SKIP)

        if res is not None:
            align_result.append([])
            for mark in res:
                res2 = {}
                for pl in mark:
                    # transforms the markings for easier correspondence at the end
                    # (distributed engine friendly!)
                    res2[(pl.name[0], pl.name[1])] = mark[pl]

                align_result[-1].append(res2)
        else:
            # if there is no path from the initial marking
            # replaying the given prefix, then add None
            align_result.append(None)

    return align_result
示例#19
0
def strongly_test():
    net = preprocess(example_graph)
    print(net)
    initial_marking = Marking()
    final_marking = Marking()
    for place in net.places:
        if place.name != "p2":
            initial_marking[place] = 1
        else:
            final_marking[place] = 1

    parameters = {
        pn_visualizer.Variants.WO_DECORATION.value.Parameters.FORMAT: "svg"
    }
    gviz = pn_visualizer.apply(net,
                               initial_marking,
                               final_marking,
                               parameters=parameters)
    pn_visualizer.save(gviz, "alpha.svg")
示例#20
0
 def decode_marking(self, ems):
     """
     Decodes a marking from a generic dictionary
     to a Marking object
     """
     em = eval(ems)
     mark = Marking()
     for p in em:
         mark[self.places_inv_dict[p]] = em[p]
     return mark
    def create_PetriNet(n):
        # label_set[0] = 'a',...,label_set[26]=z
        label_set = dict(enumerate(string.ascii_lowercase))
        if n >= 26:
            print("N is >= 26 but there are only 26 unique letters.")

        # create new petrinet
        net = PetriNet("PN")

        place_list = []
        # create start and end place
        start = PetriNet.Place("start")
        end = PetriNet.Place("end")
        net.places.add(start)
        net.places.add(end)
        place_list.insert(0, start)
        place_list.insert(n + 1, end)

        # create the rest of n-2 places (n+1 places are needed for a length n trace)
        for i in range(n - 1):
            p = PetriNet.Place(f"p{i}")
            net.places.add(p)
            place_list.insert(i + 1, p)

        transitions_list = []
        # create n transitions
        for i in range(n):
            t = PetriNet.Transition(f"t{i}", label_set[i])
            net.transitions.add(t)
            transitions_list.insert(i, t)

        for i, t in enumerate(transitions_list):
            utils.add_arc_from_to(place_list[i], t, net)
            utils.add_arc_from_to(t, place_list[i + 1], net)

        # defining initial and final marking
        im = Marking()
        im[start] = 1
        fm = Marking()
        fm[end] = 1

        return net, im
示例#22
0
def get_corresp_marking_and_trans(m, index, corresp, t):
    marking = Marking()
    marking[corresp[0][-index]] = 1
    for pl in m:
        if not corresp[1][pl] in marking:
            marking[corresp[1][pl]] = 0
        marking[corresp[1][pl]] = marking[corresp[1][pl]] + 1
    trans = None
    if t in corresp[2]:
        trans = corresp[2][t]
    return marking, trans
示例#23
0
def construct_trace_net_cost_aware(trace,
                                   costs,
                                   trace_name_key=xes_util.DEFAULT_NAME_KEY,
                                   activity_key=xes_util.DEFAULT_NAME_KEY):
    """
    Creates a trace net, i.e. a trace in Petri net form mapping specific costs to transitions.

    Parameters
    ----------
    trace: :class:`list` input trace, assumed to be a list of events
    costs: :class:`list` list of costs, length should be equal to the length of the input trace
    trace_name_key: :class:`str` key of the attribute that defines the name of the trace
    activity_key: :class:`str` key of the attribute of the events that defines the activity name

    Returns
    -------
    tuple: :class:`tuple` of the net, initial marking, final marking and map of costs


    """
    net = PetriNet('trace net of %s' %
                   trace.attributes[trace_name_key] if trace_name_key in
                   trace.attributes else ' ')
    place_map = {0: PetriNet.Place('p_0')}
    net.places.add(place_map[0])
    cost_map = dict()
    for i in range(0, len(trace)):
        t = PetriNet.Transition('t_' + trace[i][activity_key] + '_' + str(i),
                                trace[i][activity_key])
        # 16/02/2021: set the trace index as property of the transition of the trace net
        t.properties[properties.TRACE_NET_TRANS_INDEX] = i
        cost_map[t] = costs[i]
        net.transitions.add(t)
        place_map[i + 1] = PetriNet.Place('p_' + str(i + 1))
        # 16/02/2021: set the place index as property of the place of the trace net
        place_map[i + 1].properties[properties.TRACE_NET_PLACE_INDEX] = i + 1
        net.places.add(place_map[i + 1])
        add_arc_from_to(place_map[i], t, net)
        add_arc_from_to(t, place_map[i + 1], net)
    return net, Marking({place_map[0]: 1}), Marking({place_map[len(trace)]:
                                                     1}), cost_map
def __get_model_marking_and_index(marking):
    """
    Transforms a marking on the synchronous product net
    to a marking in the model and an index in the trace
    """
    mm = Marking()
    index = -1
    for p in marking:
        if properties.TRACE_NET_PLACE_INDEX in p.properties:
            index = p.properties[properties.TRACE_NET_PLACE_INDEX]
        else:
            mm[p] = marking[p]
    return mm, index
示例#25
0
def execute(t, yn, m):
    mm = Marking()
    mmm = Marking()
    m_out = copy.copy(m)

    if not is_enabled(t, yn, m):
        #if it should not be executed, just execute it and return original marking + executed marking
        for arcs in t.out_arcs:
            m[arcs.target] += 1
        return m

    for a in t.in_arcs:
        p = a.source
        if not p.is_hidden or m[p] >= a.weight:
            m_out = petri_execute(t, yn, m)
        else:
            for c in p.in_arcs:
                for d in c.source.in_arcs:
                    for e in d.source.in_arcs:
                        if e.source.is_hidden:
                            mmm = petri_execute(e.source, yn, m)
                            if mmm is not None and len(mmm) > 0:
                                break
                        if mmm is not None and len(mmm) > 0:
                            break
                    if mmm is not None and len(mmm) > 0:
                        break
                for b in p.in_arcs:
                    if mmm is not None and len(mmm) > 0:
                        mm = petri_execute(b.source, yn, mmm)
                        if mm is not None:
                            break
                    else:
                        mm = petri_execute(b.source, yn, m)
                        if mm is not None:
                            break
                m_out = petri_execute(t, yn, mm)

    return m_out
def transform_markings_from_sync_to_original_net(markings0,
                                                 net,
                                                 parameters=None):
    """
    Transform the markings of the sync net (in which alignment stops) into markings of the original net
    (in order to measure the precision)

    Parameters
    -------------
    markings0
        Markings on the sync net (expressed as place name with count)
    net
        Petri net
    parameters
        Parameters of the algorithm

    Returns
    -------------
    markings
        Markings of the original model (expressed as place with count)
    """
    if parameters is None:
        parameters = {}

    places_corr = {p.name: p for p in net.places}

    markings = []

    for i in range(len(markings0)):
        res_list = markings0[i]

        # res_list shall be a list of markings.
        # If it is None, then there is no correspondence markings
        # in the original Petri net
        if res_list is not None:
            # saves all the markings reached by the optimal alignment
            # as markings of the original net
            markings.append([])

            for j in range(len(res_list)):
                res = res_list[j]

                atm = Marking()
                for pl, count in res.items():
                    if pl[0] == utils.SKIP:
                        atm[places_corr[pl[1]]] = count
                markings[-1].append(atm)
        else:
            markings.append(None)

    return markings
示例#27
0
def decorate_transitions_prepostset(net):
    """
    Decorate transitions with sub and addition markings

    Parameters
    -------------
    net
        Petri net
    """
    from pm4py.objects.petri.petrinet import Marking
    for trans in net.transitions:
        sub_marking = Marking()
        add_marking = Marking()

        for arc in trans.in_arcs:
            sub_marking[arc.source] = arc.weight
            add_marking[arc.source] = -arc.weight
        for arc in trans.out_arcs:
            if arc.target in add_marking:
                add_marking[arc.target] = arc.weight + add_marking[arc.target]
            else:
                add_marking[arc.target] = arc.weight
        trans.sub_marking = sub_marking
        trans.add_marking = add_marking
示例#28
0
def apply(tree, parameters=None):
    """
    Conversion Process Tree to PetriNet.

    Parameters
    -----------
    tree
        Process tree
    parameters
        PARAM_CHILD_LOCK

    Returns
    -----------
    net
        Petri net
    initial_marking
        Initial marking
    final_marking
        Final marking
    """

    counts = Counts()
    net = petri.petrinet.PetriNet('imdf_net_' + str(time.time()))
    initial_marking = Marking()
    final_marking = Marking()
    source = get_new_place(counts)
    source.name = SOURCE_NAME
    sink = get_new_place(counts)
    sink.name = SINK_NAME
    net.places.add(source)
    net.places.add(sink)
    initial_marking[source] = 1
    final_marking[sink] = 1
    generate_pn(tree, net, source, sink, counts, parameters)

    return net, initial_marking, final_marking
示例#29
0
def get_initial_marking(net, max_no_comb=4):
    """
    Get the initial marking from a Petri net
    (observing which nodes are without input connection,
    if several nodes exist, then a source place is created artificially)

    Parameters
    -------------
    net
        Petri net

    Returns
    -------------
    net
        Petri net
    initial_marking
        Initial marking of the Petri net
    """
    places = set(net.places)

    places_wo_input = []
    for place in places:
        if len(place.in_arcs) == 0:
            places_wo_input.append(place)
    places_wo_input = list(places_wo_input)

    initial_marking = Marking()

    if len(places_wo_input) > 1:
        source = PetriNet.Place('petri_source')
        net.places.add(source)
        for i in range(len(places_wo_input)):
            htrans = PetriNet.Transition("itrans_" + str(i), None)
            net.transitions.add(htrans)
            utils.add_arc_from_to(source, htrans, net)
            utils.add_arc_from_to(htrans, places_wo_input[i], net)
        initial_marking[source] = 1
    elif len(places_wo_input) == 1:
        places_wo_input = list(places_wo_input)
        initial_marking[places_wo_input[0]] = 1
    return net, initial_marking
示例#30
0
def discover_initial_marking(petri):
    """
    Discovers initial marking from a Petri net

    Parameters
    ------------
    petri
        Petri net

    Returns
    ------------
    initial_marking
        Initial marking of the Petri net
    """
    initial_marking = Marking()

    for place in petri.places:
        if len(place.in_arcs) == 0:
            initial_marking[place] = 1

    return initial_marking