feat: Upload Notebook

This commit is contained in:
Louis Gallet 2024-12-14 13:58:30 +01:00
parent 3cd23deceb
commit 6910cd1f76
Signed by: lgallet
GPG Key ID: 84D3DF1528A84511
2 changed files with 678 additions and 207 deletions

446
debug.py Normal file
View File

@ -0,0 +1,446 @@
import queue
# -*- coding: utf-8 -*-
"""Graph module.
Provide an implementation of graphs with adjacency lists.
In a graph, vertices are considered numbered from 0 to the order of the graph
minus one. The vertex key can then be used to access its
adjacency list.
"""
class Graph:
""" Simple class for graph: adjacency lists
Attributes:
order (int): Number of vertices.
directed (bool): True if the graph is directed. False otherwise.
adjlists (List[List[int]]): Lists of connected vertices for each vertex.
"""
def __init__(self, order, directed, labels=None):
"""Init graph, allocate adjacency lists
Args:
order (int): Number of nodes.
directed (bool): True if the graph is directed. False otherwise.
labels (list[str]): optionnal vector of vertex labels
"""
self.order = order
self.directed = directed
self.adjlists = []
for _ in range(order):
self.adjlists.append([])
self.labels = labels
def addedge(self, src, dst):
"""Add egde to graph.
Args:
src (int): Source vertex.
dst (int): Destination vertex.
Raises:
IndexError: If any vertex index is invalid.
"""
if src >= self.order or src < 0:
raise IndexError("Invalid src index")
if dst >= self.order or dst < 0:
raise IndexError("Invalid dst index")
self.adjlists[src].append(dst)
if not self.directed and dst != src:
self.adjlists[dst].append(src)
def addvertex(self, number=1, labels=None):
"""Add number vertices to graph.
Args:
ref (Graph).
number (int): Number of vertices to add.
"""
# Increment order and extend adjacency list
self.order += number
for _ in range(number):
self.adjlists.append([])
if labels:
self.labels += labels
def removeedge(self, src, dst):
"""Remove egde from the graph.
Args:
src (int): Source vertex.
dst (int): Destination vertex.
Raises:
IndexError: If any vertex index is invalid.
"""
if src >= self.order or src < 0:
raise IndexError("Invalid src index")
if dst >= self.order or dst < 0:
raise IndexError("Invalid dst index")
if dst in self.adjlists[src]:
self.adjlists[src].remove(dst)
if not self.directed and dst != src:
self.adjlists[dst].remove(src)
def sortgraph(G):
"""
sorts adjacency lists -> to have same results as those asked in tutorials/exams
"""
for i in range(G.order):
G.adjlists[i].sort()
def dot(G):
"""Dot format of graph.
Args:
Graph
Returns:
str: String storing dot format of graph.
"""
if G.directed:
s = "digraph {\n"
for x in range(G.order):
if G.labels:
s += " " + str(x) + '[label = "' + G.labels[x] + '"]\n'
else:
s += " " + str(x) + '\n'
for y in G.adjlists[x]:
s += str(x) + " -> " + str(y) + '\n'
else:
s = "graph {\n"
for x in range(G.order):
if G.labels:
s += " " + str(x) + '[label = "' + G.labels[x] + '"]\n'
else:
s += " " + str(x) + '\n'
for y in G.adjlists[x]:
if x <= y:
s += str(x) + " -- " + str(y) + '\n'
return s + '}'
def display(G, eng=None):
"""
*Warning:* Made for use within IPython/Jupyter only.
eng: graphivz.Source "engine" optional argument (try "neato", "fdp", "sfdp", "circo")
"""
try:
from graphviz import Source
from IPython.display import display
except:
raise Exception("Missing module: graphviz and/or IPython.")
display(Source(dot(G), engine = eng))
# load / save gra format
def load(filename):
"""Build a new graph from a GRA file.
Args:
filename (str): File to load.
Returns:
Graph: New graph.
Raises:
FileNotFoundError: If file does not exist.
"""
f = open(filename)
lines = f.readlines()
f.close()
infos = {}
i = 0
while '#' in lines[i]:
(key, val) = lines[i][1:].strip().split(": ")
infos[key] = val
i += 1
directed = bool(int(lines[i]))
order = int(lines[i+1])
if infos and "labels" in infos:
labels = infos["labels"].split(',') #labels is a list of str
G = Graph(order, directed, labels) # a graph with labels
else:
G = Graph(order, directed) # a graph without labels
if infos:
G.infos = infos
for line in lines[i+2:]:
edge = line.strip().split(' ')
(src, dst) = (int(edge[0]), int(edge[1]))
G.addedge(src, dst)
return G
def save(G, fileOut):
gra = ""
if G.labels:
lab = "#labels: "
for i in range(G.order - 1):
lab += G.labels[i] + ','
lab += G.labels[-1]
gra += lab + '\n'
gra += str(int(G.directed)) + '\n'
gra += str(G.order) + '\n'
for x in range(G.order):
for y in G.adjlists[x]:
if G.directed or x >= y:
gra += str(x) + " " + str(y) + '\n'
fout = open(fileOut, mode='w')
fout.write(gra)
fout.close()
# -*- coding: utf-8 -*-
"""Graph module.
Provide an implementation of graphs with adjacency matrix.
This can also be called static implementation.
In a graph, vertices are considered numbered from 0 to the order of the graph
minus one.
"""
class GraphMat:
""" Simple class for static graph.
Attributes:
order (int): Number of vertices.
directed (bool): True if the graph is directed. False otherwise.
adj (List[List[int]]): Adjacency matrix
"""
def __init__(self, order, directed):
"""
Args:
order (int): Number of nodes.
directed (bool): True if the graph is directed. False otherwise.
"""
self.order = order
self.directed = directed
self.adj = [[0 for j in range(order)] for i in range(order)]
def addedge(self, src, dst):
"""Add egde to graph.
Args:
src (int): Source vertex.
dst (int): Destination vertex.
Raises:
IndexError: If any vertex index is invalid.
"""
if src >= self.order or src < 0:
raise IndexError("Invalid src index")
if dst >= self.order or dst < 0:
raise IndexError("Invalid dst index")
self.adj[src][dst] += 1
if not self.directed and dst != src:
self.adj[dst][src] += 1
def dot(G):
"""Dot format of graph.
Args:
GraphMat
Returns:
str: String storing dot format of graph.
"""
if G.directed:
s = "digraph {\n"
link = " -> "
for x in range(G.order):
for y in range(G.order):
s += (str(x) + link + str(y) + '\n') * G.adj[x][y]
else:
s = "graph {\n"
link = " -- "
for x in range(G.order):
for y in range(x+1):
s += (str(x) + link + str(y) + '\n') * G.adj[x][y]
return s + '}'
def display(G, eng=None):
"""
*Warning:* Made for use within IPython/Jupyter only.
eng: graphivz.Source "engine" optional argument (try "neato", "fdp", "sfdp", "circo")
"""
try:
from graphviz import Source
from IPython.display import display
except:
raise Exception("Missing module: graphviz and/or IPython.")
display(Source(dot(G), engine = eng))
# load / save gra format (do not manage labels and other infos)
def load(filename,):
"""Build a new graph from a GRA file.
Args:
filename (str): File to load.
Returns:
Graph: New graph.
Raises:
FileNotFoundError: If file does not exist.
"""
f = open(filename)
directed = bool(int(f.readline()))
order = int(f.readline())
g = GraphMat(order, directed)
for line in f.readlines():
edge = line.strip().split(' ')
(src, dst) = (int(edge[0]), int(edge[1]))
g.addedge(src, dst)
f.close()
return g
def save(G, fileOut):
gra = str(int(G.directed)) + '\n'
gra += str(G.order) + '\n'
for x in range(G.order):
if G.directed:
n = G.order
else:
n = x + 1
for y in range(n):
for i in range(G.adj[x][y]):
gra += str(x) + " " + str(y) + '\n'
fout = open(fileOut, mode='w')
fout.write(gra)
fout.close()
# -*- coding: utf-8 -*-
"""Queue module."""
from collections import deque
class Queue:
"""Simple class for FIFO (first-in-first-out) container."""
def __init__(self):
"""Init queue."""
self.elements = deque()
def enqueue(self, elt):
"""Add an element to the queue.
Args:
elt (Any): Element to enqueue.
"""
self.elements.append(elt)
def dequeue(self):
"""Remove and return next element from the queue.
Returns:
Any: Element from the queue.
Raises:
IndexError: If queue is empty.
"""
return self.elements.popleft()
def isempty(self):
"""Check whether queue is empty.
Returns:
bool: True if queue is empty, False otherwise.
"""
return len(self.elements) == 0
G = Graph(10, False)
G.adjlists = [[4, 4, 1, 3],
[0],
[6, 6, 6, 5, 7],
[0],
[0, 0, 9],
[2, 7, 8],
[2, 2, 2, 7],
[2, 6, 5, 8],
[7, 5, 8],
[4]]
def __smallest_level(G, M, src, perLevel):
cur = Queue()
cur.enqueue(src)
cur.enqueue(None)
M[src] = True
temp = []
while not cur.isempty():
x = cur.dequeue()
if x is None:
if (len(temp) != 0 and temp != [src]):
perLevel.append(temp)
temp = []
else:
temp.append(x)
for adj in G.adjlists[x]:
if not M[adj]:
M[adj] = True
cur.enqueue(adj)
cur.enqueue(None)
def smallest_level(G, src):
M = [False] * G.order
perLevel = []
__smallest_level(G, M, src, perLevel)
min = perLevel[0]
for element in perLevel:
if len(element) < len(min):
min = element
return min
smallest_level(G, 0)

View File

@ -6,8 +6,8 @@
"metadata": {
"collapsed": true,
"ExecuteTime": {
"end_time": "2024-12-14T10:54:32.699159Z",
"start_time": "2024-12-14T10:54:32.688460Z"
"end_time": "2024-12-14T12:23:31.698030Z",
"start_time": "2024-12-14T12:23:31.686929Z"
}
},
"source": [
@ -227,166 +227,26 @@
" fout.close()\n"
],
"outputs": [],
"execution_count": 3
"execution_count": 1
},
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T10:54:33.640420Z",
"start_time": "2024-12-14T10:54:33.634885Z"
"end_time": "2024-12-14T12:23:31.740543Z",
"start_time": "2024-12-14T12:23:31.738488Z"
}
},
"cell_type": "code",
"source": [
"# -*- coding: utf-8 -*-\n",
"\"\"\"Graph module.\n",
"\n",
"Provide an implementation of graphs with adjacency matrix.\n",
"This can also be called static implementation.\n",
"\n",
"In a graph, vertices are considered numbered from 0 to the order of the graph\n",
"minus one.\n",
"\n",
"\"\"\"\n",
"\n",
"\n",
"class GraphMat:\n",
" \"\"\" Simple class for static graph.\n",
"\n",
" Attributes:\n",
" order (int): Number of vertices.\n",
" directed (bool): True if the graph is directed. False otherwise.\n",
" adj (List[List[int]]): Adjacency matrix\n",
" \"\"\"\n",
"\n",
" def __init__(self, order, directed):\n",
" \"\"\"\n",
" Args:\n",
" order (int): Number of nodes.\n",
" directed (bool): True if the graph is directed. False otherwise.\n",
" \"\"\"\n",
"\n",
" self.order = order\n",
" self.directed = directed\n",
" self.adj = [[0 for j in range(order)] for i in range(order)]\n",
"\n",
"\n",
" def addedge(self, src, dst):\n",
" \"\"\"Add egde to graph.\n",
"\n",
" Args:\n",
" src (int): Source vertex.\n",
" dst (int): Destination vertex.\n",
"\n",
" Raises:\n",
" IndexError: If any vertex index is invalid.\n",
"\n",
" \"\"\"\n",
"\n",
" if src >= self.order or src < 0:\n",
" raise IndexError(\"Invalid src index\")\n",
" if dst >= self.order or dst < 0:\n",
" raise IndexError(\"Invalid dst index\")\n",
"\n",
" self.adj[src][dst] += 1\n",
" if not self.directed and dst != src:\n",
" self.adj[dst][src] += 1\n",
"\n",
"\n",
"\n",
"def dot(G):\n",
" \"\"\"Dot format of graph.\n",
"\n",
" Args:\n",
" GraphMat\n",
"\n",
" Returns:\n",
" str: String storing dot format of graph.\n",
"\n",
" \"\"\"\n",
"\n",
" if G.directed:\n",
" s = \"digraph {\\n\"\n",
" link = \" -> \"\n",
" for x in range(G.order):\n",
" for y in range(G.order):\n",
" s += (str(x) + link + str(y) + '\\n') * G.adj[x][y]\n",
" else:\n",
" s = \"graph {\\n\"\n",
" link = \" -- \"\n",
" for x in range(G.order):\n",
" for y in range(x+1):\n",
" s += (str(x) + link + str(y) + '\\n') * G.adj[x][y]\n",
" return s + '}'\n",
"\n",
"\n",
"\n",
"def display(G, eng=None):\n",
" \"\"\"\n",
" *Warning:* Made for use within IPython/Jupyter only.\n",
" eng: graphivz.Source \"engine\" optional argument (try \"neato\", \"fdp\", \"sfdp\", \"circo\")\n",
"\n",
" \"\"\"\n",
"\n",
" try:\n",
" from graphviz import Source\n",
" from IPython.display import display\n",
" except:\n",
" raise Exception(\"Missing module: graphviz and/or IPython.\")\n",
" display(Source(dot(G), engine = eng))\n",
"\n",
"\n",
"# load / save gra format (do not manage labels and other infos)\n",
"\n",
"def load(filename,):\n",
" \"\"\"Build a new graph from a GRA file.\n",
"\n",
" Args:\n",
" filename (str): File to load.\n",
"\n",
" Returns:\n",
" Graph: New graph.\n",
"\n",
" Raises:\n",
" FileNotFoundError: If file does not exist.\n",
"\n",
" \"\"\"\n",
"\n",
" f = open(filename)\n",
" directed = bool(int(f.readline()))\n",
" order = int(f.readline())\n",
" g = GraphMat(order, directed)\n",
" for line in f.readlines():\n",
" edge = line.strip().split(' ')\n",
" (src, dst) = (int(edge[0]), int(edge[1]))\n",
" g.addedge(src, dst)\n",
" f.close()\n",
" return g\n",
"\n",
"def save(G, fileOut):\n",
" gra = str(int(G.directed)) + '\\n'\n",
" gra += str(G.order) + '\\n'\n",
" for x in range(G.order):\n",
" if G.directed:\n",
" n = G.order\n",
" else:\n",
" n = x + 1\n",
" for y in range(n):\n",
" for i in range(G.adj[x][y]):\n",
" gra += str(x) + \" \" + str(y) + '\\n'\n",
" fout = open(fileOut, mode='w')\n",
" fout.write(gra)\n",
" fout.close()\n"
],
"source": "",
"id": "e12f5903c5348752",
"outputs": [],
"execution_count": 4
"execution_count": null
},
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T10:54:34.476061Z",
"start_time": "2024-12-14T10:54:34.472348Z"
"end_time": "2024-12-14T12:23:31.807702Z",
"start_time": "2024-12-14T12:23:31.804575Z"
}
},
"cell_type": "code",
@ -439,7 +299,7 @@
],
"id": "663b49e4f6763d11",
"outputs": [],
"execution_count": 5
"execution_count": 2
},
{
"metadata": {},
@ -450,8 +310,8 @@
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T10:54:38.976275Z",
"start_time": "2024-12-14T10:54:38.973873Z"
"end_time": "2024-12-14T12:23:31.826260Z",
"start_time": "2024-12-14T12:23:31.824156Z"
}
},
"cell_type": "code",
@ -471,13 +331,13 @@
],
"id": "ca54f5a3f1a225b",
"outputs": [],
"execution_count": 6
"execution_count": 3
},
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T10:54:39.957846Z",
"start_time": "2024-12-14T10:54:39.955269Z"
"end_time": "2024-12-14T12:23:31.853995Z",
"start_time": "2024-12-14T12:23:31.851762Z"
}
},
"cell_type": "code",
@ -498,7 +358,7 @@
]
}
],
"execution_count": 7
"execution_count": 4
},
{
"metadata": {},
@ -509,8 +369,8 @@
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T10:54:41.253023Z",
"start_time": "2024-12-14T10:54:41.250277Z"
"end_time": "2024-12-14T12:23:31.886996Z",
"start_time": "2024-12-14T12:23:31.884644Z"
}
},
"cell_type": "code",
@ -528,7 +388,7 @@
],
"id": "6920c423c0bdfc24",
"outputs": [],
"execution_count": 8
"execution_count": 5
},
{
"metadata": {},
@ -539,8 +399,8 @@
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-09T14:48:04.596974Z",
"start_time": "2024-12-09T14:48:04.592782Z"
"end_time": "2024-12-14T12:23:31.913924Z",
"start_time": "2024-12-14T12:23:31.909906Z"
}
},
"cell_type": "code",
@ -561,18 +421,18 @@
"[4, 1, 5, 1, 3, 3, 4, 4, 3, 1]"
]
},
"execution_count": 8,
"execution_count": 6,
"metadata": {},
"output_type": "execute_result"
}
],
"execution_count": 8
"execution_count": 6
},
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-09T14:48:05.120730Z",
"start_time": "2024-12-09T14:48:05.116518Z"
"end_time": "2024-12-14T12:23:31.946802Z",
"start_time": "2024-12-14T12:23:31.943693Z"
}
},
"cell_type": "code",
@ -596,12 +456,12 @@
"[[3, 4, 1, 2, 3, 2, 3, 0, 2], [6, 1, 1, 2, 0, 3, 2, 3, 2]]"
]
},
"execution_count": 9,
"execution_count": 7,
"metadata": {},
"output_type": "execute_result"
}
],
"execution_count": 9
"execution_count": 7
},
{
"metadata": {},
@ -612,8 +472,8 @@
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-09T14:48:06.156919Z",
"start_time": "2024-12-09T14:48:06.154020Z"
"end_time": "2024-12-14T12:23:32.018541Z",
"start_time": "2024-12-14T12:23:32.015799Z"
}
},
"cell_type": "code",
@ -696,7 +556,7 @@
]
}
],
"execution_count": 10
"execution_count": 8
},
{
"metadata": {},
@ -910,21 +770,21 @@
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-09T15:48:15.121203Z",
"start_time": "2024-12-09T15:48:15.116918Z"
"end_time": "2024-12-14T12:50:54.278706Z",
"start_time": "2024-12-14T12:50:54.271435Z"
}
},
"cell_type": "code",
"source": [
"def aux(G, M, src):\n",
" newColor = not M[src]\n",
"def aux_colors(G, M, src):\n",
" new_color = not M[src]\n",
" for adj in G.adjlists[src]:\n",
" if M[adj] == None:\n",
" M[adj] = newColor\n",
" if not aux(G, M, adj):\n",
" M[adj] = new_color\n",
" if not aux_colors(G, M, adj):\n",
" return False\n",
" else:\n",
" if M[adj] != newColor:\n",
" if M[adj] != new_color:\n",
" return False\n",
" return True\n",
"\n",
@ -934,8 +794,8 @@
" for src in range(G.order):\n",
" if M[src] == None:\n",
" M[src] = True\n",
" if not aux(G, M, src):\n",
" return False\n",
" if not aux_colors(G, M, src):\n",
" return False\n",
" return True\n",
"\n",
"two_coloring(G1)"
@ -948,12 +808,12 @@
"False"
]
},
"execution_count": 32,
"execution_count": 26,
"metadata": {},
"output_type": "execute_result"
}
],
"execution_count": 32
"execution_count": 26
},
{
"metadata": {},
@ -970,31 +830,29 @@
},
"cell_type": "code",
"source": [
"def __fakenews(G, M, src, truth):\n",
" cur = Queue()\n",
" cur.enqueue(src)\n",
"def __fakenews(G, M, src, fake):\n",
" q = Queue()\n",
" q.enqueue(src)\n",
" stop = False\n",
" while not cur.isempty() and not stop:\n",
" x = cur.dequeue()\n",
" if M[x] > truth + 1:\n",
" while not q.isempty() and not stop:\n",
" x = q.dequeue()\n",
" if M[x] > fake:\n",
" for adj in G.adjlists[x]:\n",
" if M[adj] == None:\n",
" M[adj] = M[x] - 1\n",
" cur.enqueue(adj)\n",
" q.enqueue(adj)\n",
" else:\n",
" stop = True\n",
"\n",
"def fakenews(G, src, truth):\n",
" if (truth <= 2):\n",
" raise Exception(\"truth should be > 2\")\n",
" M = [False] * G.order\n",
" M = [None] * G.order\n",
" M[src] = truth\n",
" fake = []\n",
" __fakenews(G, M, src, truth // 2)\n",
" for i in range(G.order):\n",
" if M[i] == None:\n",
" fake.append(i)\n",
" return truth"
" __fakenews(G, M, src, truth//2)\n",
" L = []\n",
" for s in range(G.order):\n",
" if M[s] == None:\n",
" L.append(s)\n",
" return L"
],
"id": "c66ac4688a6975c9",
"outputs": [],
@ -1003,24 +861,191 @@
{
"metadata": {},
"cell_type": "markdown",
"source": "# 2027 - Exercice 1",
"source": "# 2027 - Exercice 2",
"id": "b8fa23568b4bd3df"
},
{
"metadata": {},
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T12:27:17.971319Z",
"start_time": "2024-12-14T12:27:17.967991Z"
}
},
"cell_type": "code",
"outputs": [],
"execution_count": null,
"source": [
"def __longest_path(G, dist, src):\n",
"# Reconstitution du graph du partiel\n",
"# Initialisation d'un graphe non orienté avec 10 sommets\n",
"G = Graph(order=10, directed=False)\n",
"\n",
"# Ajout des arêtes selon l'image fournie\n",
"G.addedge(0, 1)\n",
"G.addedge(0, 2)\n",
"G.addedge(0, 8)\n",
"G.addedge(0, 6)\n",
"G.addedge(1, 2)\n",
"G.addedge(1, 3)\n",
"G.addedge(2, 3)\n",
"G.addedge(2, 8)\n",
"G.addedge(3, 5)\n",
"G.addedge(3, 6)\n",
"G.addedge(4, 5)\n",
"G.addedge(5, 7)\n",
"G.addedge(6, 9)\n",
"G.addedge(7, 9)\n",
"G.addedge(8, 9)\n",
"\n",
"def longest_path(G):\n",
" dist = [None] * G.order\n",
" for src in range(G.order):\n",
" __longest_path(G, dist, src)"
"# Tri des listes d'adjacence pour une sortie cohérente\n",
"sortgraph(G)\n",
"\n",
"# Affichage du graphe au format DOT (si tu as graphviz configuré)\n",
"print(dot(G))\n",
"\n",
"# Affichage visuel dans Jupyter Notebook (optionnel)\n",
"# display(G, eng=\"neato\") # Utilise l'option \"neato\" pour une disposition automatique"
],
"id": "9a3a85d15dccbb97"
"id": "f3f003f5ecd72f9e",
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"digraph {\n",
"0 -- 1\n",
"0 -- 2\n",
"0 -- 6\n",
"0 -- 8\n",
"1 -- 0\n",
"1 -- 2\n",
"1 -- 3\n",
"2 -- 0\n",
"2 -- 1\n",
"2 -- 3\n",
"2 -- 8\n",
"3 -- 1\n",
"3 -- 2\n",
"3 -- 5\n",
"3 -- 6\n",
"4 -- 5\n",
"5 -- 3\n",
"5 -- 4\n",
"5 -- 7\n",
"6 -- 0\n",
"6 -- 3\n",
"6 -- 9\n",
"7 -- 5\n",
"7 -- 9\n",
"8 -- 0\n",
"8 -- 2\n",
"8 -- 9\n",
"9 -- 6\n",
"9 -- 7\n",
"9 -- 8\n",
"}\n"
]
}
],
"execution_count": 15
},
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T12:42:59.642392Z",
"start_time": "2024-12-14T12:42:59.636696Z"
}
},
"cell_type": "code",
"source": [
"\"\"\"\n",
"def __smallest_level(G, M, src, perLevel):\n",
" cur = Queue()\n",
" cur.enqueue(src)\n",
" cur.enqueue(None)\n",
" M[src] = True\n",
" temp = []\n",
" while not cur.isempty():\n",
" x = cur.dequeue()\n",
" if x is None:\n",
" if (len(temp) != 0 and temp != [src]):\n",
" perLevel.append(temp)\n",
" temp = []\n",
" else:\n",
" temp.append(x)\n",
" for adj in G.adjlists[x]:\n",
" if not M[adj]:\n",
" M[adj] = True\n",
" cur.enqueue(adj)\n",
" cur.enqueue(None)\n",
"\n",
"def smallest_level(G, src):\n",
" M = [False] * G.order\n",
" perLevel = []\n",
" __smallest_level(G, M, src, perLevel)\n",
" min = perLevel[0]\n",
" for element in perLevel:\n",
" if len(element) < len(min):\n",
" min = element\n",
" return min\n",
"\"\"\"\n",
"\n",
"def smallest(G, src):\n",
" dist = [None] * G.order\n",
" q = Queue()\n",
" q.enqueue(src)\n",
" dist[src] = 0\n",
" small = G.order\n",
" d = 0\n",
" L = []\n",
" while not q.isempty():\n",
" x = q.dequeue()\n",
" if dist[x] > d:\n",
" if len(L) < small:\n",
" small = len(L)\n",
" Res = L\n",
" d += 1\n",
" L = []\n",
" for y in G.adjlists[x]:\n",
" if dist[y] == None:\n",
" dist[y] = dist[x] + 1\n",
" q.enqueue(y)\n",
" L.append(y)\n",
" return Res"
],
"id": "9a3a85d15dccbb97",
"outputs": [],
"execution_count": 23
},
{
"metadata": {
"ExecuteTime": {
"end_time": "2024-12-14T12:43:03.858284Z",
"start_time": "2024-12-14T12:43:03.855864Z"
}
},
"cell_type": "code",
"source": [
"for s in range(10):\n",
" print(s, \"=>\", smallest(G, s))"
],
"id": "5be240ac4da2b002",
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"0 => [4]\n",
"1 => [0, 2, 3]\n",
"2 => [4, 7]\n",
"3 => [1, 2, 5, 6]\n",
"4 => [5]\n",
"5 => [0, 8]\n",
"6 => [4]\n",
"7 => [5, 9]\n",
"8 => [5]\n",
"9 => [1, 4]\n"
]
}
],
"execution_count": 24
}
],
"metadata": {