{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Visualizing the topic and accessibility of scholarly articles cited in Wikipedia\n", "\n", "Building on a dataset we previously released of [citations with identifiers](https://doi.org/10.6084/m9.figshare.1299540.v10) across all Wikipedia language editions, we explore the distribution of [DOIs](https://en.wikipedia.org/wiki/Digital_object_identifier) cited in Wikipedia by *topic* and *accessibility*.\n", "\n", "## Topic\n", "We assign a *topic* to each publication, by looking at the main topic(s) of the Wikipedia article that cites it. Topics are determined by matching each article with its [WikiProject](https://en.wikipedia.org/wiki/Wikipedia:WikiProject), and assigning the corresponding top-level topic according to the [Wikiproject Hierarchy](https://figshare.com/articles/WikiProjects_Machine_Readable_Dataset/5503819/1). This is done using the [draftopic tool](https://github.com/wiki-ai/drafttopic) from the Wikimedia Foundation's Scoring Platform team.\n", "\n", "## Accessibility\n", "We determine the *accessibility* of each publication (by looking up the DOI in data provided by [Unpaywall](http://unpaywall.org/data-format). The DOI is marked as:\n", "* *Open*: if the canonical version is open access at the source (journal); \n", "* *Available*: if the canonical version at the source is behind a paywall, but an open access copy is available at a different location; \n", "* *Closed*: if the canonical version at the source is behind a paywall and not open access copy was identified at a different location\n", "\n", "Note that this analysis only takes into account the openness of the canonical version of a scholarly paper citation as identified by a DOI. Citation templates used in Wikipedia articles often complement a DOI with a link to an accessible version, when it has identified.\" \n", "## Dataset documentation\n", "Further documentation on the format of the data can be found in the parent dataset: [https://doi.org/10.6084/m9.figshare.1299540.v10](https://doi.org/10.6084/m9.figshare.1299540.v10)" ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [], "source": [ "'''\n", "import useful libraries\n", "'''\n", "import pandas as pd\n", "import numpy as np\n", "from bokeh.models import ColumnDataSource, LabelSet, HoverTool,Range1d, NumeralTickFormatter\n", "from bokeh.plotting import figure, show, output_file\n", "from bokeh.io import output_notebook\n", "from bokeh.transform import stack\n", "\n", "import math\n", "import operator\n", "import sys\n", "import warnings\n", "\n", "if not sys.warnoptions:\n", " warnings.simplefilter(\"ignore\")\n", "\n", "''' use input file provided or substitute with your own path '''\n", "inputfile='data/all_data_forplot.tsv'\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### We define the three functions to discover relations between publication topic, language and accessibility\n", "* Breakdown of total number of publications and percentage of open/available publications by language, for a specific topic or for all topics\n", "* Breakdown of total number of publications and percentage of open/available publications by topic, for a specific language or for all languages\n", "* Breakdown of publications by type and topic, for all topics\n" ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [], "source": [ "\n", "def generate_open_language_plot(dataframe,open_type,topic):\n", " '''\n", " takes as input:\n", " dataframe - the pandas data frame containing the data\n", " open_type - 'open' if you want to visualize completely open access statistics; \n", " 'avaliable if you want to visualize statistics about publications having free copies available;\n", " topic - a string corresponding to one of the topics, or 'all' if you want to have \n", " a complete overview across topics. Choose between:\n", " 'Africa', 'Americas', 'Article improvement and grading', 'Arts', 'Biology', 'Bodies of water', \n", " 'Broadcasting', 'Business and economics', 'Chemistry', 'Cities', 'Contents systems','Countries', \n", " 'Crafts and hobbies', 'Economics', 'Education','Entertainment', 'Europe', 'Files', \n", " 'Food and drink', 'Geosciences','History and society', 'Information science', 'Internet culture',\n", " 'Landforms', 'Language and literature', 'Maintenance', 'Maps', 'Mathematics', 'Media', 'Medicine', \n", " 'Meteorology', 'Military and warfare', 'Music', 'Performing arts','Philosophy and religion', \n", " 'Physics', 'Plastic arts','Politics and government', 'Science', 'Space', 'Sports','Technology', \n", " 'Time', 'Transportation', 'all'\n", " '''\n", " if open_type=='open':\n", " text='open access'\n", " elif open_type=='available':\n", " text='available open access'\n", " else:\n", " print('wrong accessibility type')\n", " return\n", " if topic == 'all':\n", " topic= 'all_topics'\n", " TITLE = \"Percentage of \"+text+\" publications for all topics\"\n", " else:\n", " TITLE = \"Percentage of \"+text+\" publications for topic \"+topic\n", " \n", " #load the data for one specific topic\n", " source=ColumnDataSource(dataframe.loc[dataframe['topic'] == topic])\n", " \n", " #prepare interaction tools\n", " tools = \"pan,wheel_zoom,box_zoom,reset,save\".split(',')\n", " hover = HoverTool(tooltips=[\n", " (\"language\", \"@wiki\"),\n", " (\"total scholarly publications:\", \"@{total}{0}\"),\n", " (\"% open publications\", \"@{open}{0.00%}\"),\n", " (\"% open access available publications\", \"@{available}{0.00%}\")])\n", " tools.append(hover)\n", " \n", " #prepare the plot figure, depending on the quantity of data, go for log scale or linear scale\n", " if max(dataframe.loc[dataframe['topic'] == topic]['total']>500):\n", " p = figure(tools=tools, toolbar_location=\"above\", logo=\"grey\", \n", " plot_width=800, plot_height=600, title=TITLE,y_axis_type=\"log\")\n", " else:\n", " p = figure(tools=tools, toolbar_location=\"above\", logo=\"grey\", \n", " plot_width=800, plot_height=600, title=TITLE)\n", " \n", " #prepare plot background, axes labels and line colors\n", " p.background_fill_color = \"#ffffff\" #change if you don't want white background\n", " p.xaxis.axis_label = \"percentage of \"+text+\" publications\"\n", " p.yaxis.axis_label = \"total number of scholarly publications\"\n", " p.grid.grid_line_color = \"gray\"\n", "\n", " #choose format for axes\n", " p.yaxis[0].formatter = NumeralTickFormatter(format=\"0\")\n", " p.xaxis[0].formatter = NumeralTickFormatter(format=\"0.00%\")\n", " \n", " #draw the circles; change colors here\n", " p.circle(open_type, \"total\", size=10, \n", " source=source, line_color=\"#005693\", line_width=1,\n", " line_alpha=0.7, fill_alpha=0.5, fill_color=\"#23a3ff\")\n", " labels = LabelSet(x=open_type, y=\"total\", text=\"wiki\",y_offset=8,\n", " text_font_size=\"8pt\", text_color=\"#555555\",\n", " source=source, text_align='center')\n", " p.add_layout(labels)\n", " \n", " #draws the plot\n", " output_notebook()\n", " show(p)\n", "\n", "\n", "def generate_open_topic_plot(df,topics, open_type,lan):\n", " '''\n", " takes as input:\n", " df - the pandas data frame containing the data\n", " open_type - 'open' if you want to visualize completely open access statistics; \n", " 'avaliable if you want to visualize statistics about publications having free copies available;\n", " lan - a string corresponding to one of the languages for which we have data, or 'all' if you want to have \n", " a complete overview across all languages. Choose between:\n", " 'ace', 'af', 'ak', 'als', 'am', 'an', 'ang', 'ar', 'arz', 'as', 'ast', 'av', 'az', 'azb', 'ba', \n", " 'bar', 'bat_smg', 'bcl', 'be', 'be_x_old', 'bg', 'bh', 'bjn', 'bn', 'bo', 'bpy', 'br', 'bs', 'bxr',\n", " 'cbk_zam', 'cdo', 'ce', 'ceb', 'chr', 'ckb', 'co', 'cs', 'csb', 'cu', 'cv', 'cy', 'da', 'de', 'diq',\n", " 'dsb', 'dty', 'dv', 'ee', 'el', 'eml', 'en', 'eo', 'es', 'et', 'eu', 'ext', 'fa', 'fi', 'fo', 'fr',\n", " 'frr', 'fy', 'ga', 'gag', 'gan', 'gd', 'gl', 'gn', 'gom', 'gu', 'gv', 'ha', 'hak', 'hi', 'hif', 'hr',\n", " 'hsb', 'ht', 'hu', 'hy', 'ia', 'id', 'ie', 'ig', 'ilo', 'io', 'is', 'it', 'ja', 'jam', 'jbo', 'jv',\n", " 'ka', 'kab', 'kk', 'km', 'kn', 'ko', 'koi', 'krc', 'ku', 'kv', 'ky', 'la', 'lad', 'lb', 'lez', 'lg', \n", " 'li', 'lij', 'lmo', 'ln', 'lo', 'lrc', 'lt', 'lv', 'mai', 'map_bms', 'mdf', 'mg', 'mhr', 'min', 'mk',\n", " 'ml', 'mn', 'mr', 'mrj', 'ms', 'mt', 'mwl', 'my', 'myv', 'mzn', 'na', 'nah', 'nds', 'nds_nl', 'ne', \n", " 'new', 'nl', 'nn', 'no', 'nov', 'nso', 'nv', 'ny', 'oc', 'olo', 'om', 'or', 'os', 'pa', 'pam', 'pap', \n", " 'pcd', 'pfl', 'pi', 'pih', 'pl', 'pms', 'pnb', 'ps', 'pt', 'qu', 'rm', 'ro', 'roa_tara', 'ru', 'rue',\n", " 'rw', 'sa', 'sah', 'sc', 'scn', 'sco', 'sd', 'se', 'sh', 'si', 'simple', 'sk', 'sl', 'sm', 'sn', 'so', \n", " 'sq', 'sr', 'ss', 'st', 'stq', 'su', 'sv', 'sw', 'szl', 'ta', 'tcy', 'te', 'test', 'test2', 'tet', 'tg',\n", " 'th', 'ti', 'tl', 'tn', 'tr', 'ts', 'tt', 'ug', 'uk', 'ur', 'uz', 'vec', 'vep', 'vi', 'vls', 'vo', 'war',\n", " 'wo', 'wuu', 'xh', 'xmf', 'yi', 'yo', 'za', 'zh', 'zh_classical', 'zh_min_nan', 'zh_yue','all'\n", " '''\n", " #we are now going to generate a new dataframe gathering for each topic either the values for one language, \n", " #or the average/sum of values across languages\n", " dic={}\n", " counts={}\n", " if open_type=='open':\n", " text='open access'\n", " elif open_type=='available':\n", " text='available open access'\n", " else:\n", " print('wrong accessibility type')\n", " return\n", " if lan=='all':\n", " for topic in topics:\n", " if topic=='all_topics': \n", " continue\n", " dic[topic]=np.mean(df.loc[df['topic']==topic].loc[df['wiki']=='all_languages'][open_type])\n", " counts[topic]=np.sum(df.loc[df['topic']==topic].loc[df['wiki']=='all_languages']['total'])\n", " TITLE = \"Percentage of \"+text+\" publications by topic for all languages\"\n", " else:\n", " for topic in topics:\n", " if topic=='all_topics': \n", " continue\n", " dic[topic]=np.mean(df.loc[df['topic']==topic].loc[df['wiki']==lan][open_type])\n", " counts[topic]=np.sum(df.loc[df['topic']==topic].loc[df['wiki']==lan]['total'])\n", " TITLE = \"Percentage of \"+text+\" publications for \"+lan+\".Wikipedia\"\n", " source = pd.DataFrame(data={'topics':dic.keys(), 'counts':counts.values(), 'perc':dic.values()}) \n", " #prepare interaction tools\n", " tools = \"pan,wheel_zoom,box_zoom,reset,save\".split(',')\n", " hover = HoverTool(tooltips=[\n", " (\"topic\", \"@topics\"),\n", " (\"total scholarly publications:\", \"@{counts}{0}\"),\n", " (\"% \"+text+\" publications\", \"@{perc}{0.00%}\")])\n", " tools.append(hover)\n", " \n", " #prepare the plot figure, depending on the quantity of data, go for log scale or linear scale\n", " if max(source['counts']>200):\n", " p = figure(tools=tools, toolbar_location=\"above\", logo=\"grey\", plot_width=800, plot_height=600, title=TITLE,y_axis_type=\"log\")\n", " else:\n", " p = figure(tools=tools, toolbar_location=\"above\", logo=\"grey\", plot_width=800, plot_height=600, title=TITLE)\n", " p.background_fill_color = \"#ffffff\"\n", " \n", " #change axes labels according to whether we analyze one language or all languages, prepare axes\n", " if lan=='all':\n", " p.xaxis.axis_label = \"average percentage of \"+text+\" publications across languages\"\n", " p.yaxis.axis_label = \"sum of all scholarly publications across languages\"\n", " else:\n", " p.xaxis.axis_label = \"percentage of \"+text+\" publications\"\n", " p.yaxis.axis_label = \"total number of scholarly publications\"\n", " p.x_range=Range1d(0,1.1)\n", " p.yaxis[0].formatter = NumeralTickFormatter(format=\"0\")\n", " p.xaxis[0].formatter = NumeralTickFormatter(format=\"0.00%\")\n", " p.grid.grid_line_color = \"gray\"\n", " \n", " #draw the circles; change colors here\n", " source = ColumnDataSource(source)\n", " p.circle(\"perc\", \"counts\", size=10, source=source, line_color=\"#8B0A50\", line_width=1,line_alpha=0.7, fill_alpha=0.5, fill_color=\"#cd1076\")\n", " labels = LabelSet(x=\"perc\", y=\"counts\", text=\"topics\",y_offset=8,\n", " text_font_size=\"8pt\", text_color=\"#555555\",\n", " source=source, text_align='center')\n", " p.add_layout(labels)\n", " \n", " #draw plot\n", " output_notebook()\n", " show(p)\n", "\n", "\n", "\n", "def generate_comparison_plot(dataframe,topics):\n", " '''\n", " takes as input:\n", " dataframe - the pandas data frame containing the data\n", " '''\n", " TITLE = \"Percentage of open, available, and closed publications for all topics\"\n", " header=['open','available','closed']\n", " #prepare interaction tools\n", " tools = \"pan,wheel_zoom,box_zoom,reset,save\".split(',')\n", " hover = HoverTool(tooltips=[\n", " (\"topic\", \"@topic\"),\n", " (\"total scholarly publications:\", \"@{total}{0}\"),\n", " (\"% open publications\", \"@{open}{0.00%}\"),\n", " (\"% OA available publications\", \"@{available}{0.00%}\"),\n", " (\"% paywalled publications\", \"@{closed}{0.00%}\")])\n", " tools.append(hover)\n", " dic=df.loc[df['wiki']=='all_languages']\n", " #print dic\n", " p = figure(y_range=topics,tools=tools, toolbar_location=\"above\", logo=\"grey\", plot_width=800, title=TITLE)\n", " #p.background_fill_color = \"#ffffff\" #change if you don't want white background\n", "\n", " #choose format for axes\n", " \n", " source = ColumnDataSource(dic)\n", "\n", " p.hbar_stack(header,y='topic',height=0.5,source=source, color=['#5F9E99','#ffb06e','#e72d66'])\n", " \n", " #p.hbar(right=stack(),left=stack('open'),y='topic',height=0.2,color='blue',source=source,name='open')\n", " #p.hbar(right=stack('open'),left=stack('open', 'available'), y='topic', height=0.2, color='red',source=source,name='available')\n", "\n", " p.legend.visible=True\n", "\n", " #draws the plot\n", " output_notebook()\n", " show(p)\n", "\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We now read the input data and store set of languages and topics available (for future usage)\n" ] }, { "cell_type": "code", "execution_count": 11, "metadata": {}, "outputs": [], "source": [ "\n", "\n", "df = pd.DataFrame.from_csv(inputfile,sep='\\t', index_col=None)\n", "wikis = list(np.sort(list(set(df['wiki'].tolist()))))\n", "topics =list(set(df['topic'].tolist()))\n", "topics=np.delete(topics,[topics.index('all_topics'),topics.index('Article improvement and grading')])\n", "topics= np.sort(topics)[::-1]\n", "\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We now generate the distribution of languages over the real accessibility ('open') and potential accessibility ('available') of their publications, for all topics" ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [ { "data": { "text/html": [ "\n", "
" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "application/javascript": [ "\n", "(function(root) {\n", " function now() {\n", " return new Date();\n", " }\n", "\n", " var force = true;\n", "\n", " if (typeof (root._bokeh_onload_callbacks) === \"undefined\" || force === true) {\n", " root._bokeh_onload_callbacks = [];\n", " root._bokeh_is_loading = undefined;\n", " }\n", "\n", " var JS_MIME_TYPE = 'application/javascript';\n", " var HTML_MIME_TYPE = 'text/html';\n", " var EXEC_MIME_TYPE = 'application/vnd.bokehjs_exec.v0+json';\n", " var CLASS_NAME = 'output_bokeh rendered_html';\n", "\n", " /**\n", " * Render data to the DOM node\n", " */\n", " function render(props, node) {\n", " var script = document.createElement(\"script\");\n", " node.appendChild(script);\n", " }\n", "\n", " /**\n", " * Handle when an output is cleared or removed\n", " */\n", " function handleClearOutput(event, handle) {\n", " var cell = handle.cell;\n", "\n", " var id = cell.output_area._bokeh_element_id;\n", " var server_id = cell.output_area._bokeh_server_id;\n", " // Clean up Bokeh references\n", " if (id !== undefined) {\n", " Bokeh.index[id].model.document.clear();\n", " delete Bokeh.index[id];\n", " }\n", "\n", " if (server_id !== undefined) {\n", " // Clean up Bokeh references\n", " var cmd = \"from bokeh.io.state import curstate; print(curstate().uuid_to_server['\" + server_id + \"'].get_sessions()[0].document.roots[0]._id)\";\n", " cell.notebook.kernel.execute(cmd, {\n", " iopub: {\n", " output: function(msg) {\n", " var element_id = msg.content.text.trim();\n", " Bokeh.index[element_id].model.document.clear();\n", " delete Bokeh.index[element_id];\n", " }\n", " }\n", " });\n", " // Destroy server and session\n", " var cmd = \"import bokeh.io.notebook as ion; ion.destroy_server('\" + server_id + \"')\";\n", " cell.notebook.kernel.execute(cmd);\n", " }\n", " }\n", "\n", " /**\n", " * Handle when a new output is added\n", " */\n", " function handleAddOutput(event, handle) {\n", " var output_area = handle.output_area;\n", " var output = handle.output;\n", "\n", " // limit handleAddOutput to display_data with EXEC_MIME_TYPE content only\n", " if ((output.output_type != \"display_data\") || (!output.data.hasOwnProperty(EXEC_MIME_TYPE))) {\n", " return\n", " }\n", "\n", " var toinsert = output_area.element.find(\".\" + CLASS_NAME.split(' ')[0]);\n", "\n", " if (output.metadata[EXEC_MIME_TYPE][\"id\"] !== undefined) {\n", " toinsert[toinsert.length - 1].firstChild.textContent = output.data[JS_MIME_TYPE];\n", " // store reference to embed id on output_area\n", " output_area._bokeh_element_id = output.metadata[EXEC_MIME_TYPE][\"id\"];\n", " }\n", " if (output.metadata[EXEC_MIME_TYPE][\"server_id\"] !== undefined) {\n", " var bk_div = document.createElement(\"div\");\n", " bk_div.innerHTML = output.data[HTML_MIME_TYPE];\n", " var script_attrs = bk_div.children[0].attributes;\n", " for (var i = 0; i < script_attrs.length; i++) {\n", " toinsert[toinsert.length - 1].firstChild.setAttribute(script_attrs[i].name, script_attrs[i].value);\n", " }\n", " // store reference to server id on output_area\n", " output_area._bokeh_server_id = output.metadata[EXEC_MIME_TYPE][\"server_id\"];\n", " }\n", " }\n", "\n", " function register_renderer(events, OutputArea) {\n", "\n", " function append_mime(data, metadata, element) {\n", " // create a DOM node to render to\n", " var toinsert = this.create_output_subarea(\n", " metadata,\n", " CLASS_NAME,\n", " EXEC_MIME_TYPE\n", " );\n", " this.keyboard_manager.register_events(toinsert);\n", " // Render to node\n", " var props = {data: data, metadata: metadata[EXEC_MIME_TYPE]};\n", " render(props, toinsert[toinsert.length - 1]);\n", " element.append(toinsert);\n", " return toinsert\n", " }\n", "\n", " /* Handle when an output is cleared or removed */\n", " events.on('clear_output.CodeCell', handleClearOutput);\n", " events.on('delete.Cell', handleClearOutput);\n", "\n", " /* Handle when a new output is added */\n", " events.on('output_added.OutputArea', handleAddOutput);\n", "\n", " /**\n", " * Register the mime type and append_mime function with output_area\n", " */\n", " OutputArea.prototype.register_mime_type(EXEC_MIME_TYPE, append_mime, {\n", " /* Is output safe? */\n", " safe: true,\n", " /* Index of renderer in `output_area.display_order` */\n", " index: 0\n", " });\n", " }\n", "\n", " // register the mime type if in Jupyter Notebook environment and previously unregistered\n", " if (root.Jupyter !== undefined) {\n", " var events = require('base/js/events');\n", " var OutputArea = require('notebook/js/outputarea').OutputArea;\n", "\n", " if (OutputArea.prototype.mime_types().indexOf(EXEC_MIME_TYPE) == -1) {\n", " register_renderer(events, OutputArea);\n", " }\n", " }\n", "\n", " \n", " if (typeof (root._bokeh_timeout) === \"undefined\" || force === true) {\n", " root._bokeh_timeout = Date.now() + 5000;\n", " root._bokeh_failed_load = false;\n", " }\n", "\n", " var NB_LOAD_WARNING = {'data': {'text/html':\n", " \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"\\n\"+\n", " \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n", " \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n", " \"
\\n\"+\n", " \"\\n\"+\n",
" \"from bokeh.resources import INLINE\\n\"+\n",
" \"output_notebook(resources=INLINE)\\n\"+\n",
" \"
\\n\"+\n",
" \"\\n\"+\n \"BokehJS does not appear to have successfully loaded. If loading BokehJS from CDN, this \\n\"+\n \"may be due to a slow or bad network connection. Possible fixes:\\n\"+\n \"
\\n\"+\n \"\\n\"+\n \"from bokeh.resources import INLINE\\n\"+\n \"output_notebook(resources=INLINE)\\n\"+\n \"
\\n\"+\n \"