{ "cells": [ { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Spectral partitioning" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We examine a data mining task of clustering a graph which defines a network of relationships. We collect data from a forum where posters can quote each other in reply to other posts. We define our data such that there exists a relationship between two people when they quote each other, i.e. if `A` quotes `B` in a post, then a relationship exists between `A` and `B`, and vice versa. If `C` makes a post on the thread, but does not quote anyone, then `C` has no relationship with any of the posters on the thread. \n", "\n", "We visualize these relationships between any two poster as a directed graph. The direction of the edges indicate who quotes who. We can define this as a relationship between `source` and `target`. A user in the `source` column has made a post and quotes the `target`. Multiple quotes have been separated into separate observations." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The overarching objective is to determine is there is any information latent in the nature of interaction on any particular thread. Some of the hypotheses include the possibility that a group of posters interact significantly more with each other and as a result form a cluster which exists somewhat independently of other groups of posters on the same thread. In any case, posters who had little or no interaction with others in the thread are very likely to stand apart from the giant cluster of active contributors." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Collecting the data**. Here the code implements the data collection from the forum thread of interest. This code is particular to the forum of interest and will change depending on the nature of interaction with the `html` page. We use `BeautifulSoup` to extract the information residing in the tags." ] }, { "cell_type": "code", "execution_count": 287, "metadata": {}, "outputs": [], "source": [ "from bs4 import BeautifulSoup\n", "import requests\n", "import pandas as pd\n", "import json\n", "import re" ] }, { "cell_type": "code", "execution_count": 288, "metadata": {}, "outputs": [], "source": [ "#URL page\n", "link = 'https://www.nairaland.com/4945611/thread-tutorial-python-programming/'" ] }, { "cell_type": "code", "execution_count": 289, "metadata": {}, "outputs": [], "source": [ "def getNodes(link):\n", " nodes = {}\n", " k = 0\n", "\n", " for i in range(27): #link has 27 pages\n", " url = link + str(i)\n", " html = requests.get(url)\n", " soup = BeautifulSoup(html.content)\n", " tnodes = {} #Temporary nodes\n", " print('Downloading page...',i, end='\\r')\n", " for i, j in zip(soup.find_all('td', {'class': 'bold l pu'}), \n", " soup.find_all('td', {'class': 'l w pd'})):\n", " if i.find('a', {'class': 'user'}):\n", " tnodes['user'] = i.find('a', {'class': 'user'}).string\n", " else:\n", " tnodes['user'] = '?'\n", " quoted = []\n", " x = (j.find_all('blockquote'))\n", " if x == []:\n", " tnodes['quoted'] = []\n", " else:\n", " n = 0\n", " while n < len(x):\n", " if x[n].a is not None:\n", " if re.match(pattern='/post/\\d*$', string=x[n].a['href']):\n", " quoted.append(x[n].a.b.string)\n", " n += 1\n", " tnodes['quoted'] = quoted\n", " nodes[k] = tnodes \n", " k += 1\n", " tnodes = {}\n", " return nodes" ] }, { "cell_type": "code", "execution_count": 290, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Downloading page... 26\r" ] } ], "source": [ "mnodes = getNodes(link)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We get a dictionary which contains information about each `user` and the poster quoted given as `quoted`. A peek into the resulting dictionary shows `user`-`quoted` pairs. For posts where no one is quoted, `quoted` is an empty list, while for `user` who has `quoted` another poster, `quoted` is a list containing that poster's username. for `user` who has quoted another poster multiple times, `quoted`, which is defined as a list, contains all of the posters that have been quoted. '?' is used to indicate unavailable posters." ] }, { "cell_type": "code", "execution_count": 296, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "{\n", " \"0\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": []\n", " },\n", " \"1\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": []\n", " },\n", " \"2\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": []\n", " },\n", " \"3\": {\n", " \"user\": \"Ikennablue\",\n", " \"quoted\": []\n", " },\n", " \"4\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": []\n", " },\n", " \"5\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": [\n", " \"Ikennablue\"\n", " ]\n", " }\n", "}\n" ] } ], "source": [ "print(json.dumps({key: value for key, value in list(mnodes.items())[:6]}, \n", " indent=4))" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We extract only keys where a relationship exists, i.e. keys where `quoted` is not null, while expanding any list of multiple quoted posters." ] }, { "cell_type": "code", "execution_count": 303, "metadata": {}, "outputs": [], "source": [ "enodes = {}\n", "k = 0\n", "for i, j in mnodes.items():\n", " for m in range(len(j['quoted'])):\n", " enodes[k+m] = {}\n", " enodes[k+m]['user'] = j['user'] \n", " for n in range(len(j['quoted'])):\n", " enodes[k+n]['quoted'] = j['quoted'][n]\n", " k += 1" ] }, { "cell_type": "code", "execution_count": 308, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "{\n", " \"5\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": \"Ikennablue\"\n", " },\n", " \"24\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": \"Prefola\"\n", " },\n", " \"27\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": \"Ibruks\"\n", " },\n", " \"31\": {\n", " \"user\": \"Paapii3d\",\n", " \"quoted\": \"yusman14\"\n", " },\n", " \"32\": {\n", " \"user\": \"KellaKella\",\n", " \"quoted\": \"STENON\"\n", " },\n", " \"34\": {\n", " \"user\": \"wasiubello\",\n", " \"quoted\": \"Paapii3d\"\n", " }\n", "}\n" ] } ], "source": [ "print(json.dumps({key: value for key, value in list(enodes.items())[:6]}, \n", " indent=4))" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Creating Graph**. We have defined the relationships which exist between posters based on whether they are quoted or not. We envisage \"quoting\" as a form of interaction between any two posters. We now create the desired graph by defining `source` and `target` elements in our graph network." ] }, { "cell_type": "code", "execution_count": 155, "metadata": {}, "outputs": [], "source": [ "from networkx.convert_matrix import from_pandas_edgelist\n", "from networkx.drawing.nx_pylab import draw\n", "from networkx import DiGraph\n", "from networkx.drawing import circular_layout\n", "\n", "import matplotlib.pyplot as plt\n", "import numpy as np\n", "import scipy as sp\n", "import pandas as pd\n" ] }, { "cell_type": "code", "execution_count": 435, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
userquoted
0Paapii3dIkennablue
1Paapii3dPrefola
2Paapii3dIbruks
3Paapii3dyusman14
4KellaKellaSTENON
\n", "
" ], "text/plain": [ " user quoted\n", "0 Paapii3d Ikennablue\n", "1 Paapii3d Prefola\n", "2 Paapii3d Ibruks\n", "3 Paapii3d yusman14\n", "4 KellaKella STENON" ] }, "execution_count": 435, "metadata": {}, "output_type": "execute_result" } ], "source": [ "edges = pd.DataFrame(enodes).T.reset_index(drop=True)\n", "edges.head()" ] }, { "cell_type": "code", "execution_count": 436, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "user 270\n", "quoted 270\n", "dtype: int64" ] }, "execution_count": 436, "metadata": {}, "output_type": "execute_result" } ], "source": [ "edges.count()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We have a total of 270 observations in the dataset. However, some nodes are empty. These are indicated using '?'." ] }, { "cell_type": "code", "execution_count": 437, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
userquoted
19?Paapii3d
44?Henrique99
88?nappy760
90?nappy760
117?Paapii3d
\n", "
" ], "text/plain": [ " user quoted\n", "19 ? Paapii3d\n", "44 ? Henrique99\n", "88 ? nappy760\n", "90 ? nappy760\n", "117 ? Paapii3d" ] }, "execution_count": 437, "metadata": {}, "output_type": "execute_result" } ], "source": [ "edges[(edges.user=='?') | (edges.quoted=='?')].head()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We remove these empty nodes and provide the columns with more convenient names: `source` and `target`, showing the relationship between the nodes in the directed graph. " ] }, { "cell_type": "code", "execution_count": 438, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
userquoted
0Paapii3dIkennablue
1Paapii3dPrefola
2Paapii3dIbruks
3Paapii3dyusman14
4KellaKellaSTENON
.........
265Teejay13mikael4me
266onecodernaijasensei
267naijasenseionecoder
268binghammernaijasensei
269binghammeronecoder
\n", "

263 rows × 2 columns

\n", "
" ], "text/plain": [ " user quoted\n", "0 Paapii3d Ikennablue\n", "1 Paapii3d Prefola\n", "2 Paapii3d Ibruks\n", "3 Paapii3d yusman14\n", "4 KellaKella STENON\n", ".. ... ...\n", "265 Teejay13 mikael4me\n", "266 onecoder naijasensei\n", "267 naijasensei onecoder\n", "268 binghammer naijasensei\n", "269 binghammer onecoder\n", "\n", "[263 rows x 2 columns]" ] }, "execution_count": 438, "metadata": {}, "output_type": "execute_result" } ], "source": [ "edges[(edges.user!='?') & (edges.quoted!='?')]" ] }, { "cell_type": "code", "execution_count": 439, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
sourcetarget
0Paapii3dIkennablue
1Paapii3dPrefola
2Paapii3dIbruks
3Paapii3dyusman14
4KellaKellaSTENON
\n", "
" ], "text/plain": [ " source target\n", "0 Paapii3d Ikennablue\n", "1 Paapii3d Prefola\n", "2 Paapii3d Ibruks\n", "3 Paapii3d yusman14\n", "4 KellaKella STENON" ] }, "execution_count": 439, "metadata": {}, "output_type": "execute_result" } ], "source": [ "edges = (edges[(edges.user!='?') & (edges.quoted!='?')]\n", " .reset_index(drop=True)\n", " .rename(columns={'user': 'source', 'quoted': 'target'}))\n", "edges.head()" ] }, { "cell_type": "code", "execution_count": 440, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Total number of directed relationships in graph ==> 263\n" ] } ], "source": [ "print(f'Total number of directed relationships in graph ==> {edges.__len__()}')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "As mentioned earlier, we visualize the relationship between `source` and `target` as a `A`-quotes-`B` relationship. A representation of this relationship is shown below for the first few observations in the dataset." ] }, { "cell_type": "code", "execution_count": 441, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "relationships = edges.head(7)\n", "G = from_pandas_edgelist(relationships, source='source', target='target',\n", " create_using=DiGraph())\n", "plt.figure(figsize=(6,6))\n", "draw(G, arrows=True, with_labels=True, pos=circular_layout(G),\n", " node_size=5000, node_color=None, font_color='white',\n", " width=2, arrowsize=20)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Our dataset probably has a few duplicate observations where `A` quotes `B` multiple times. We need no more than one instance of such interaction and will therefore eliminate duplicate observations. We will also symmetrize the edges so that we convert the graph into an undirected one. For our purposes, whether `A` quotes `B` or `B` quotes `A` is irrelevant. We only need confirmation of any interaction between `A` and `B`. This ensures that we obtain an adjacency matrix, $A$." ] }, { "cell_type": "code", "execution_count": 442, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
sourcetarget
0Paapii3dIkennablue
1Paapii3dPrefola
2Paapii3dIbruks
3Paapii3dyusman14
4KellaKellaSTENON
\n", "
" ], "text/plain": [ " source target\n", "0 Paapii3d Ikennablue\n", "1 Paapii3d Prefola\n", "2 Paapii3d Ibruks\n", "3 Paapii3d yusman14\n", "4 KellaKella STENON" ] }, "execution_count": 442, "metadata": {}, "output_type": "execute_result" } ], "source": [ "def getSymmetrizedDf(edges):\n", " edges_copy = edges.copy()\n", " edges_copy = edges_copy.rename(columns={'source': 'target','target':'source'})\n", " fedges = pd.concat([edges, edges_copy], axis=0)\n", " return fedges.drop_duplicates().reset_index(drop=True)\n", " \n", "# Demo of your function:\n", "relm = getSymmetrizedDf(edges)\n", "relm.head()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We convert the dataframe into a sparse matrix where the entry is 1 if there is a relationship between `source` and `target`. Otherwise it is 0. The numerical ID of each node is determined from the `nodes` dataframe. The dimensions of the sparse matrix will be $n \\times n$, where $n$ is 1 plus the largest ID in `nodes.index`." ] }, { "cell_type": "code", "execution_count": 519, "metadata": {}, "outputs": [], "source": [ "nodes = pd.DataFrame(relm.source.unique()).rename(columns={0: 'name'})" ] }, { "cell_type": "code", "execution_count": 520, "metadata": {}, "outputs": [], "source": [ "def getSparseMatrix(nodes, edges):\n", " \n", " from scipy.sparse import coo_matrix\n", " n = nodes.index.max() + 1\n", " name_to_id = dict(zip(nodes['name'], nodes.index))\n", " values = np.ones(len(edges))\n", " rows = edges.source.apply(lambda x: name_to_id[x])\n", " cols = edges.target.apply(lambda x: name_to_id[x])\n", " A = coo_matrix((values, (rows, cols)), shape=(n,n))\n", " return A \n" ] }, { "cell_type": "code", "execution_count": 522, "metadata": {}, "outputs": [], "source": [ "A = getSparseMatrix(nodes, relm)" ] }, { "cell_type": "code", "execution_count": 521, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "(167, 167)" ] }, "execution_count": 521, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.shape" ] }, { "cell_type": "code", "execution_count": 523, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plt.figure(figsize=(7, 7))\n", "plt.spy(A, markersize=2, markeredgecolor='black');" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Mining Relationships**. A plot of the sparse matrix shows the relationship existent between the nodes. Our objective is to cluster this relationship based on how connceted the nodes are. To realize this, we use the graph Laplacian, defined as $L = D - A$, where $A$ is the matrix of symmetrized relationships defined earlier and $D$ is the diagonal matrix consisting of the degree of every node. We use spectral graph partioning which is a graph partitioning technique based on the eigenvalues and eigenvectors of the Laplacian matrix of a graph to derive the communities present in the data." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The Laplacian is symmetric since it is derived from another symmetric matrix. Its eigenvalues are also non-negative. Its smallest eigenvalue is 0, but the second smallest and its corresponding eigenvector encode significant information about the relationship between the nodes in the matrix. We exploit this fact to cluster the nodes." ] }, { "cell_type": "code", "execution_count": 524, "metadata": {}, "outputs": [], "source": [ "def partition_inds_by_sign(x):\n", " r_x = np.argwhere(x>0).flatten()\n", " l_x = np.argwhere(x<=0).flatten()\n", " return r_x, l_x\n", "\n", "def invert_perm(k):\n", " return np.array(list(zip(*sorted(list(zip(np.arange(len(k)),k)), \n", " key=lambda x: x[1])))[0])" ] }, { "cell_type": "code", "execution_count": 525, "metadata": {}, "outputs": [], "source": [ "def calc_fiedler_vector(A):\n", " from scipy.sparse import spdiags\n", " from scipy.sparse.linalg import eigsh\n", " n = min(A.shape)\n", " D = spdiags(A.sum(axis=1).reshape(n), diags=0, m=A.shape[0], n=A.shape[1])\n", " L = D - A # Laplacian\n", " _, V = eigsh(L, k=2, which='SM') # Determine 2nd smallest eigenpair\n", " return V[:, 1]\n", "\n", "v = calc_fiedler_vector(A)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "When data is partitioned using the fielder vector (corresponding eigenvector of second smallest eigenvalue), we form two groups. One from components with positive sign, and the other from components with non-positive sign. The plot below indicates how the fielder vector splits the data." ] }, { "cell_type": "code", "execution_count": 526, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plt.plot(sorted(v));" ] }, { "cell_type": "code", "execution_count": 527, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "=== Group 0 ===\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
name
1KellaKella
7STENON
24Adesuwa147
32babajeje123
35princesweetman2
48Slymking
62ssappsnwebs
63eboigbedavid1
78Raalsalghul
79ges2019
80DriggityDre
94Enemetronics
140mirajpress
143mayor6254
146kiddkash
152Internet247
154King1982
155Sanquine
159whitelotus
160omoowhe
\n", "
" ], "text/plain": [ " name\n", "1 KellaKella\n", "7 STENON\n", "24 Adesuwa147\n", "32 babajeje123\n", "35 princesweetman2\n", "48 Slymking\n", "62 ssappsnwebs\n", "63 eboigbedavid1\n", "78 Raalsalghul\n", "79 ges2019\n", "80 DriggityDre\n", "94 Enemetronics\n", "140 mirajpress\n", "143 mayor6254\n", "146 kiddkash\n", "152 Internet247\n", "154 King1982\n", "155 Sanquine\n", "159 whitelotus\n", "160 omoowhe" ] }, "metadata": {}, "output_type": "display_data" }, { "name": "stdout", "output_type": "stream", "text": [ "\n", "=== Group 1 ===\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
name
0Paapii3d
2wasiubello
3drvalency
4yusman14
5sweetilicious
......
162Vicogrin
163Lolo24
164IFIRI
165Nonychinonso
166Luckybelt
\n", "

147 rows × 1 columns

\n", "
" ], "text/plain": [ " name\n", "0 Paapii3d\n", "2 wasiubello\n", "3 drvalency\n", "4 yusman14\n", "5 sweetilicious\n", ".. ...\n", "162 Vicogrin\n", "163 Lolo24\n", "164 IFIRI\n", "165 Nonychinonso\n", "166 Luckybelt\n", "\n", "[147 rows x 1 columns]" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "k_g, k_l = partition_inds_by_sign(v)\n", "\n", "print(\"=== Group 0 ===\")\n", "display(nodes.loc[k_g])\n", "\n", "print(\"\\n=== Group 1 ===\")\n", "display(nodes.loc[k_l])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We end up with two groups of data, which when plotted produce the relationship shown below" ] }, { "cell_type": "code", "execution_count": 528, "metadata": {}, "outputs": [], "source": [ "def reorder_by_fiedler(A, v):\n", " from scipy.sparse import coo_matrix\n", " assert isinstance(A, type(coo_matrix((1, 1))))\n", "\n", " r_v, l_v = partition_inds_by_sign(v)\n", " ind = np.concatenate((r_v, l_v))\n", " v_dict = dict(zip(ind, np.arange(len(ind))))\n", " \n", " A_n_row = [v_dict[i] for i in A.row]\n", " A_n_col = [v_dict[i] for i in A.col]\n", " \n", " A_perm = coo_matrix((A.data, (A_n_row, A_n_col)), shape=A.shape)\n", " return A_perm\n", "\n", " \n", "A_perm = reorder_by_fiedler(A, v)" ] }, { "cell_type": "code", "execution_count": 529, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plt.figure(figsize=(7, 7))\n", "plt.spy(A_perm, markersize=2, markeredgecolor='black')\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The graph above shows the two groups inherent in the data based on interaction between posters. In this particular dataset, the main center of interaction is the original poster (OP) who is `Paapii3d`. The groups appear to be divided based on those who have or did not have interactions with the OP. When the individual groups are examined, we find that `Group 0` users are less likely to have interacted with `Paapii3d`, while users in `Group 1` are more likely to have interacted with the OP. The average number of interactions in `Group 0` is about 1.1, while the average number of interactions in `Group 1` is much higher at 2.12." ] }, { "cell_type": "code", "execution_count": 547, "metadata": {}, "outputs": [], "source": [ "group0, group1 = [], []\n", "for name in nodes.loc[k_g].values:\n", " group0.append(relm[relm['source'] == name[0]].count().loc['source'])\n", "\n", "for name in nodes.loc[k_l].values:\n", " group1.append(relm[relm['source'] == name[0]].count().loc['source'])" ] }, { "cell_type": "code", "execution_count": 546, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Average number of interactions in Group 0 ==> 1.1\n", "Average number of interactions in Group 1 ==> 2.12\n" ] } ], "source": [ "print(f'Average number of interactions in Group 0 ==> {round(sum(group0) / group0.__len__(), 2)}')\n", "print(f'Average number of interactions in Group 1 ==> {round(sum(group1) / group1.__len__(), 2)}')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## References" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Weisstein, Eric W. \"Spectral Graph Partitioning.\" From MathWorld--A Wolfram Web Resource. https://mathworld.wolfram.com/SpectralGraphPartitioning.html\n", "\n", "Weisstein, Eric W. \"Laplacian Matrix.\" From MathWorld--A Wolfram Web Resource. https://mathworld.wolfram.com/LaplacianMatrix.html\n", "\n", "Sikdar, S. \"Spectral Community Detection.\" Retrieved from https://www3.nd.edu/~kogge/courses/cse60742-Fall2018/Public/StudentWork/KernelPaperFinal/SCD-Sikdar-final.pdf" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "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.8.3" } }, "nbformat": 4, "nbformat_minor": 4 }