Skip to content
This repository has been archived by the owner on Aug 7, 2020. It is now read-only.

Commit

Permalink
Implementação do Simulator (#12)
Browse files Browse the repository at this point in the history
* Created module sim with both the DiscreteEventSimulator class and an implementation of it in it.

* Changed file structure. Added notebook for testing the code.

* Added python cache and notebook folders to git ignore
  • Loading branch information
maacarvalho authored May 15, 2020
1 parent 7d66b3d commit 22e51d0
Show file tree
Hide file tree
Showing 12 changed files with 265 additions and 68 deletions.
8 changes: 7 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,10 @@
.vscode/

# DS_Store
.DS_Store
.DS_Store

# Jupyter Notebook files
.ipynb_checkpoints/

# Python Cache files
__pycache__/
12 changes: 0 additions & 12 deletions DiscreteEventSimulator.py

This file was deleted.

2 changes: 0 additions & 2 deletions GraphAlgoritms.py

This file was deleted.

31 changes: 0 additions & 31 deletions Node.py

This file was deleted.

22 changes: 0 additions & 22 deletions NodeImplementation.py

This file was deleted.

58 changes: 58 additions & 0 deletions main.ipynb
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
{
"cells": [
{
"cell_type": "code",
"execution_count": 11,
"metadata": {},
"outputs": [
{
"output_type": "execute_result",
"data": {
"text/plain": "[<HybridRole.PRIMARY: 1>, 'GOSSIP', 'Hello World!']"
},
"metadata": {},
"execution_count": 11
}
],
"source": [
"from nodes.hybrid import HybridNode, HybridRole, MessageType\n",
"\n",
"node = HybridNode (0, HybridRole.PRIMARY, [])\n",
"\n",
"msg = (MessageType.GOSSIP, 1000, \"Hello World!\")\n",
"\n",
"node.handle(1, msg)\n"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"from sim.faulty import FaultySimulator"
]
}
],
"metadata": {
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.7.6-final"
},
"orig_nbformat": 2,
"kernelspec": {
"name": "python37664bitf145e88782004c4e8f08cdfdceda798c",
"display_name": "Python 3.7.6 64-bit"
}
},
"nbformat": 4,
"nbformat_minor": 2
}
1 change: 1 addition & 0 deletions nodes/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
__all__ = ["node", "hybrid"]
86 changes: 86 additions & 0 deletions nodes/hybrid.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
from .node import Node

from enum import Enum

class HybridNode (Node):

# - id: identification number
# - role: node role in the network
# - neighbors: adjacent nodes id's
def __init__ (self, id, role, neighbors):

self.id = id
self.role = role
self.neighbors = neighbors


def handle (self, src, data):

# unpacking data
type, id, payload = data

# handling different types of messages
if type is MessageType.GOSSIP:

return self.__gossip__(src, id, payload)

elif type is MessageType.IHAVE:

return self.__ihave__(src, id)

elif type is MessageType.ASK:

return self.__ask__(src, id)

elif type is MessageType.PERIODIC:

return self.__periodic__(src, id)

elif type is MessageType.GC:

return self.__gc__(src)

else:

return []


def __gossip__ (self, src, id, payload):

return [self.role, "GOSSIP", payload]

def __ihave__ (self, src, id):

return []

def __ack__ (self, src, id):

return []

def __ask__ (self, src, id):

return []

def __periodic__ (self, src, id):

return []

def __gc__ (self, src):

return []

# different types of messages recognized by this type of node
class MessageType(Enum):

GOSSIP = 1
IHAVE = 2
ASK = 3
PERIODIC = 4
GC = 5
ACK = 6

# different types of hybrid node
class HybridRole (Enum):

PRIMARY = 1
SECUNDARY = 2
6 changes: 6 additions & 0 deletions nodes/node.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
class Node:

# returns e.g. [(dst0, msg0), (dst1, msg1), ...]
def handle (self, src, data):

pass
1 change: 1 addition & 0 deletions sim/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
__all__ = ["sim", "faulty"]
100 changes: 100 additions & 0 deletions sim/faulty.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
from .sim import DiscreteEventSimulator

import random

class FaultySimulator (DiscreteEventSimulator):

# - nodes: graph nodes
# - distances: distances between each node
# - fault_chance: probability of losing a message in simulation
def __init__(self, nodes, distances, fault_chance = 0):

# nodes
self.nodes = nodes

# distances between nodes
self.distances = distances

# simulator current instant tracker
self.current_instant = 0

# events pending execution [(instant, (src, dst, data))]
self.pending = []

# probability of losing an event
self.fault_chance = fault_chance

def start(self, initial_data, initial_node):

# starting randomizer
random.seed()

# creating first event [instant, (src, dst, data)]
instant, src, dst, data = 0, None, initial_node, initial_data

# schedule first event
self.pending.append( (instant, (src, dst, data )) )

# run the loop
return self.__loop__()

def __loop__(self):

# creating a sorted event list
ordered_events = []

# running loop
while len(self.pending) > 0:

# getting the event with lowest instant
event = min (self.pending, key = lambda e:e[0])

# unfolding event properties
instant, src, dst, data = event[0], event[1][0], event[1][1], event[1][2]

# printing event
# print(str(instant) + "s :: " + str(src) + " -> " + str(dst) + " :: " + str(data))

# removing event from the queue
self.pending.remove(event)

# skipping event based on fault probability
if random.random() < self.fault_chance:

# skipping iteration
continue

# executing event if event is valid
if (src, dst) in self.distances or src is None:

# appending event to sorted event list
ordered_events.append(event)

# generating new events from event
self.__exec__(event)

# returning sorted event list
return ordered_events

def __exec__ (self, event):

# unfolding event properties
instant, src, dst, data = event[0], event[1][0], event[1][1], event[1][2]

# node handling event and generating new datas
new_datas = self.nodes[dst].handle(src, data)

# update src node
new_src = dst

# generating events for each data
for (new_dst, new_data, delay) in new_datas:

# get distance to node
distance = self.distances[(new_src, new_dst)]

# creating new event
new_event = (instant + distance + delay, (new_src, new_dst, new_data))

# appending event to pending
self.pending.append(new_event)
6 changes: 6 additions & 0 deletions sim/sim.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
class DiscreteEventSimulator:

# returns list of events ordered by time
def start(self, initial_data, initial_node):

pass

0 comments on commit 22e51d0

Please sign in to comment.