{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Chapter 19: Social Network Analysis\n",
    "\n",
    "> (c) 2019 Galit Shmueli, Peter C. Bruce, Peter Gedeck \n",
    ">\n",
    "> Code included in\n",
    ">\n",
    "> _Data Mining for Business Analytics: Concepts, Techniques, and Applications in Python_ (First Edition) \n",
    "> Galit Shmueli, Peter C. Bruce, Peter Gedeck, and Nitin R. Patel. 2019.\n",
    "\n",
    "## Import required packages"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:48.357855Z",
     "iopub.status.busy": "2021-05-27T20:03:48.357352Z",
     "iopub.status.idle": "2021-05-27T20:03:49.315366Z",
     "shell.execute_reply": "2021-05-27T20:03:49.314859Z"
    }
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "no display found. Using non-interactive Agg backend\n"
     ]
    }
   ],
   "source": [
    "from pathlib import Path\n",
    "\n",
    "import collections\n",
    "import pandas as pd\n",
    "import networkx as nx\n",
    "import matplotlib.pyplot as plt\n",
    "\n",
    "import dmba\n",
    "\n",
    "%matplotlib inline\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Figure 19.1 \n",
    " "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:49.335852Z",
     "iopub.status.busy": "2021-05-27T20:03:49.333421Z",
     "iopub.status.idle": "2021-05-27T20:03:49.463125Z",
     "shell.execute_reply": "2021-05-27T20:03:49.462734Z"
    }
   },
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 21016 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Build a dataframe that defines the edges and use to build the graph\n",
    "df = pd.DataFrame([\n",
    "    (\"Dave\", \"Jenny\"), (\"Peter\", \"Jenny\"), (\"John\", \"Jenny\"),\n",
    "    (\"Dave\", \"Peter\"), (\"Dave\", \"John\"), (\"Peter\", \"Sam\"),\n",
    "    (\"Sam\", \"Albert\"), (\"Peter\", \"John\")\n",
    "], columns=['from', 'to'])\n",
    "G = nx.from_pandas_edgelist(df, 'from', 'to')\n",
    " \n",
    "# Plot it\n",
    "nx.draw(G, with_labels=True, node_color='lightblue', node_size=1600)\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Figure 19.2"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:49.490200Z",
     "iopub.status.busy": "2021-05-27T20:03:49.467483Z",
     "iopub.status.idle": "2021-05-27T20:03:49.656964Z",
     "shell.execute_reply": "2021-05-27T20:03:49.656484Z"
    }
   },
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 19196 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "# generate and plot graph\n",
    "# use nx.DiGraph to create a directed graph\n",
    "G = nx.from_pandas_edgelist(df, 'from', 'to', create_using=nx.DiGraph())\n",
    "\n",
    "nx.draw(G, with_labels=True, node_color='lightblue', node_size=1600)\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Figure 19.4 DRUG LAUNDRY NETWORK IN SAN ANTONIO, TX"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:49.661494Z",
     "iopub.status.busy": "2021-05-27T20:03:49.660822Z",
     "iopub.status.idle": "2021-05-27T20:03:49.793923Z",
     "shell.execute_reply": "2021-05-27T20:03:49.793475Z"
    }
   },
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 23144 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "drug_df = dmba.load_data('drug.csv')\n",
    "\n",
    "G = nx.from_pandas_edgelist(drug_df, 'Entity', 'Related Entity')\n",
    "\n",
    "centrality = nx.eigenvector_centrality(G)\n",
    "\n",
    "nx.draw(G, with_labels=False, node_color='skyblue', node_size=[400*centrality[n] for n in G.nodes()])\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Figure 19.5"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:49.799368Z",
     "iopub.status.busy": "2021-05-27T20:03:49.798940Z",
     "iopub.status.idle": "2021-05-27T20:03:50.010871Z",
     "shell.execute_reply": "2021-05-27T20:03:50.010445Z"
    }
   },
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 34816 characters]\n",
      "text/plain": [
       "<Figure size 720x288 with 2 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "G = nx.from_pandas_edgelist(df, 'from', 'to')\n",
    "\n",
    "plt.subplots(nrows=1, ncols=2, figsize=(10, 4))\n",
    "\n",
    "plt.subplot(121)\n",
    "nx.draw_circular(G, with_labels=True, node_color='lightblue', node_size=1600)\n",
    "plt.subplot(122)\n",
    "nx.draw_kamada_kawai(G, with_labels=True, node_color='lightblue', node_size=1600)\n",
    "plt.tight_layout()\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Table 19.2 Adjacency matrix"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.015391Z",
     "iopub.status.busy": "2021-05-27T20:03:50.014953Z",
     "iopub.status.idle": "2021-05-27T20:03:50.017780Z",
     "shell.execute_reply": "2021-05-27T20:03:50.017371Z"
    }
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "[[0. 1. 1. 1. 0. 0.]\n",
      " [0. 0. 0. 0. 0. 0.]\n",
      " [0. 1. 0. 1. 1. 0.]\n",
      " [0. 1. 0. 0. 0. 0.]\n",
      " [0. 0. 0. 0. 0. 1.]\n",
      " [0. 0. 0. 0. 0. 0.]]\n"
     ]
    }
   ],
   "source": [
    "G = nx.from_pandas_edgelist(df, 'from', 'to', create_using=nx.DiGraph())\n",
    "print(nx.to_numpy_matrix(G))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.023069Z",
     "iopub.status.busy": "2021-05-27T20:03:50.022623Z",
     "iopub.status.idle": "2021-05-27T20:03:50.114690Z",
     "shell.execute_reply": "2021-05-27T20:03:50.114176Z"
    }
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "[('Dave', 3), ('Jenny', 3), ('Peter', 4), ('John', 3), ('Sam', 2), ('Albert', 1)]\n",
      "Centrality: \n",
      "{'Dave': 0.625, 'Jenny': 0.625, 'Peter': 0.8333333333333334, 'John': 0.625, 'Sam': 0.625, 'Albert': 0.4166666666666667}\n",
      "Betweenness: \n",
      "{'Dave': 0.0, 'Jenny': 0.0, 'Peter': 6.0, 'John': 0.0, 'Sam': 4.0, 'Albert': 0.0}\n",
      "{'Dave': 0.0, 'Jenny': 0.0, 'Peter': 0.6000000000000001, 'John': 0.0, 'Sam': 0.4, 'Albert': 0.0}\n",
      "Eigenvector centrality: \n",
      "{'Dave': 0.47246979363344, 'Jenny': 0.47246979363344, 'Peter': 0.528716197637421, 'John': 0.47246979363344, 'Sam': 0.2105222549863287, 'Albert': 0.08035200571997278}\n"
     ]
    },
    {
     "data": {
      "image/png": "[encoded data, 20108 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "G = nx.from_pandas_edgelist(df, 'from', 'to')\n",
    "print(G.degree())\n",
    "print('Centrality: ')\n",
    "print(nx.closeness_centrality(G))\n",
    "\n",
    "print('Betweenness: ')\n",
    "print(nx.betweenness_centrality(G, normalized=False))\n",
    "print(nx.betweenness_centrality(G))\n",
    "\n",
    "print('Eigenvector centrality: ')\n",
    "print(nx.eigenvector_centrality(G, tol=1e-2))\n",
    "v = nx.eigenvector_centrality(G, tol=1e-2).values()\n",
    "\n",
    "nx.draw_kamada_kawai(G, with_labels=True, node_color='lightblue', node_size=1600)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.121781Z",
     "iopub.status.busy": "2021-05-27T20:03:50.121309Z",
     "iopub.status.idle": "2021-05-27T20:03:50.125628Z",
     "shell.execute_reply": "2021-05-27T20:03:50.125204Z"
    }
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "{'Dave': 0.0, 'Jenny': 0.0, 'Peter': 0.6000000000000001, 'John': 0.0, 'Sam': 0.4, 'Albert': 0.0}\n",
      "{'Dave': 0.175, 'Jenny': 0.175, 'Peter': 0.675, 'John': 0.175, 'Sam': 0.4, 'Albert': 0.0}\n"
     ]
    }
   ],
   "source": [
    "print(nx.betweenness_centrality(G))\n",
    "print(nx.current_flow_betweenness_centrality(G))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.145556Z",
     "iopub.status.busy": "2021-05-27T20:03:50.142423Z",
     "iopub.status.idle": "2021-05-27T20:03:50.332199Z",
     "shell.execute_reply": "2021-05-27T20:03:50.331738Z"
    }
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "['Dave', 'Jenny', 'Peter', 'John', 'Sam', 'Albert']\n"
     ]
    },
    {
     "data": {
      "image/png": "[encoded data, 28996 characters]\n",
      "text/plain": [
       "<Figure size 720x288 with 2 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "print(G.nodes)\n",
    "\n",
    "plt.subplots(nrows=1, ncols=2, figsize=(10, 4))\n",
    "\n",
    "plt.subplot(121)\n",
    "G_ego = nx.ego_graph(G, 'Peter')\n",
    "nx.draw(G_ego, with_labels=True, node_color='lightblue', node_size=1600)\n",
    "plt.subplot(122)\n",
    "G_ego = nx.ego_graph(G, 'Peter', radius=2)\n",
    "nx.draw(G_ego, with_labels=True, node_color='lightblue', node_size=1600)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Table 19.5"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.337056Z",
     "iopub.status.busy": "2021-05-27T20:03:50.336602Z",
     "iopub.status.idle": "2021-05-27T20:03:50.340543Z",
     "shell.execute_reply": "2021-05-27T20:03:50.340164Z"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[0, 1, 1, 3, 1]"
      ]
     },
     "execution_count": 1,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "degreeCount = collections.Counter(d for node, d in G.degree())\n",
    "degreeDistribution = [0] * (1 + max(degreeCount))\n",
    "for degree, count in degreeCount.items():\n",
    "    degreeDistribution[degree] = count\n",
    "degreeDistribution"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.344454Z",
     "iopub.status.busy": "2021-05-27T20:03:50.343948Z",
     "iopub.status.idle": "2021-05-27T20:03:50.347244Z",
     "shell.execute_reply": "2021-05-27T20:03:50.346868Z"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "Counter({3: 3, 4: 1, 2: 1, 1: 1})"
      ]
     },
     "execution_count": 1,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "degreeCount = collections.Counter(d for node, d in G.degree())\n",
    "degreeCount"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.350819Z",
     "iopub.status.busy": "2021-05-27T20:03:50.350354Z",
     "iopub.status.idle": "2021-05-27T20:03:50.353491Z",
     "shell.execute_reply": "2021-05-27T20:03:50.353889Z"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "0.5333333333333333"
      ]
     },
     "execution_count": 1,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "nx.density(G)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.357566Z",
     "iopub.status.busy": "2021-05-27T20:03:50.357107Z",
     "iopub.status.idle": "2021-05-27T20:03:50.360427Z",
     "shell.execute_reply": "2021-05-27T20:03:50.360068Z"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[0.0, 0.16666666666666666, 0.16666666666666666, 0.5, 0.16666666666666666]"
      ]
     },
     "execution_count": 1,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "[d / sum(degreeDistribution) for d in degreeDistribution]  # normalized"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Table 19.11"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 14,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.365395Z",
     "iopub.status.busy": "2021-05-27T20:03:50.364955Z",
     "iopub.status.idle": "2021-05-27T20:03:50.446520Z",
     "shell.execute_reply": "2021-05-27T20:03:50.446130Z"
    }
   },
   "outputs": [],
   "source": [
    "import os\n",
    "from twython import Twython  \n",
    "\n",
    "credentials = {}  \n",
    "credentials['CONSUMER_KEY'] = os.environ.get('TWITTER_CONSUMER_KEY', None)\n",
    "credentials['CONSUMER_SECRET'] = os.environ.get('TWITTER_CONSUMER_SECRET', None)\n",
    "\n",
    "if not (credentials['CONSUMER_KEY'] is None and credentials['CONSUMER_SECRET'] is None):\n",
    "    python_tweets = Twython(credentials['CONSUMER_KEY'], credentials['CONSUMER_SECRET'])\n",
    "\n",
    "    # Create our query\n",
    "    query = {'q': 'text mining', 'result_type': 'recent',\n",
    "            'count': 25, 'lang': 'en'}\n",
    "\n",
    "    recentTweets = python_tweets.search(**query)\n",
    "    for tweet in recentTweets['statuses'][:2]:\n",
    "        print(tweet['text'])"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "E.g.\n",
    "\n",
    "```\n",
    "RT @data_nerd: Text Mining 101: What it Is and How it Works - DZone Big Data https://t.co/zLyzX1NHJS\n",
    "RT @sciencedirect: What if you could access only the information you needed instead of having to sift through all the information that is p…\n",
    "```"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Table 19.2"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {
    "execution": {
     "iopub.execute_input": "2021-05-27T20:03:50.451372Z",
     "iopub.status.busy": "2021-05-27T20:03:50.450944Z",
     "iopub.status.idle": "2021-05-27T20:03:50.454043Z",
     "shell.execute_reply": "2021-05-27T20:03:50.453658Z"
    }
   },
   "outputs": [],
   "source": [
    "token = '<access token>'\n",
    "if token != '<access token>':  # skip execution if token is not available\n",
    "    import facebook\n",
    "    graph = facebook.GraphAPI(access_token=token)\n",
    "    results = graph.request('/dataminingbook/posts?fields=likes.summary(true),message,created_time&limit=10')\n",
    "    pd.DataFrame([\n",
    "        {\n",
    "            'created_time': d.get('created_time', ''),\n",
    "            'message': d.get('message', ''),\n",
    "            'likes': d.get('likes', {}).get('summary', {}).get('total_count', 0),\n",
    "        } for d in results['data']])"
   ]
  },
  {
   "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.9.2"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
