{"cells": [{"cell_type": "markdown", "metadata": {}, "source": ["# Time processing for every ONNX nodes in a graph\n", "\n", "The following notebook show how long the runtime spends in each node of an ONNX graph."]}, {"cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [{"data": {"text/html": ["
\n", ""], "text/plain": [""]}, "execution_count": 2, "metadata": {}, "output_type": "execute_result"}], "source": ["from jyquickhelper import add_notebook_menu\n", "add_notebook_menu()"]}, {"cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [], "source": ["%load_ext mlprodict"]}, {"cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [], "source": ["%matplotlib inline"]}, {"cell_type": "markdown", "metadata": {}, "source": ["## LogisticRegression"]}, {"cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [{"data": {"text/plain": ["LogisticRegression(solver='liblinear')"]}, "execution_count": 5, "metadata": {}, "output_type": "execute_result"}], "source": ["from sklearn.datasets import load_iris\n", "from sklearn.model_selection import train_test_split\n", "from sklearn.linear_model import LogisticRegression\n", "iris = load_iris()\n", "X, y = iris.data, iris.target\n", "X_train, X_test, y_train, y_test = train_test_split(X, y)\n", "clr = LogisticRegression(solver='liblinear')\n", "clr.fit(X_train, y_train)"]}, {"cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", ""], "text/plain": [""]}, "execution_count": 6, "metadata": {}, "output_type": "execute_result"}], "source": ["import numpy\n", "from mlprodict.onnx_conv import to_onnx\n", "onx = to_onnx(clr, X_test.astype(numpy.float32))\n", "with open(\"logreg_time.onnx\", \"wb\") as f:\n", " f.write(onx.SerializeToString())\n", "# add -l 1 if nothing shows up\n", "%onnxview onx"]}, {"cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " i \n", " name \n", " op_type \n", " time \n", " \n", " \n", " \n", " \n", " 0 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.199603 \n", " \n", " \n", " 1 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000091 \n", " \n", " \n", " 2 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000014 \n", " \n", " \n", " 3 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000016 \n", " \n", " \n", "
\n", "
"], "text/plain": [" i name op_type time\n", "0 0 LinearClassifier LinearClassifier 0.199603\n", "1 1 Normalizer Normalizer 0.000091\n", "2 2 Cast Cast 0.000014\n", "3 3 ZipMap ZipMap 0.000016"]}, "execution_count": 7, "metadata": {}, "output_type": "execute_result"}], "source": ["from mlprodict.onnxrt import OnnxInference\n", "import pandas\n", "oinf = OnnxInference(onx)\n", "res = oinf.run({'X': X_test}, node_time=True)\n", "pandas.DataFrame(list(res[1]))"]}, {"cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [{"data": {"text/plain": ["{0: array([8.38235830e-01, 1.21554664e-03, 6.97352537e-04, 7.93823160e-01,\n", " 9.24825077e-01]),\n", " 1: array([0.16162989, 0.39692812, 0.25688601, 0.20607722, 0.07516498]),\n", " 2: array([1.34279470e-04, 6.01856333e-01, 7.42416637e-01, 9.96200831e-05,\n", " 9.94208860e-06])}"]}, "execution_count": 8, "metadata": {}, "output_type": "execute_result"}], "source": ["oinf.run({'X': X_test})['output_probability'][:5]"]}, {"cell_type": "markdown", "metadata": {}, "source": ["## Measure time spent in each node\n", "\n", "\n", "With parameter ``node_time=True``, method *run* returns the output and time measurement."]}, {"cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [{"data": {"text/plain": ["[{'i': 0,\n", " 'name': 'LinearClassifier',\n", " 'op_type': 'LinearClassifier',\n", " 'time': 0.00015699999999974068},\n", " {'i': 1,\n", " 'name': 'Normalizer',\n", " 'op_type': 'Normalizer',\n", " 'time': 5.43000000003957e-05},\n", " {'i': 2, 'name': 'Cast', 'op_type': 'Cast', 'time': 1.1699999999947863e-05},\n", " {'i': 3,\n", " 'name': 'ZipMap',\n", " 'op_type': 'ZipMap',\n", " 'time': 1.940000000111297e-05}]"]}, "execution_count": 9, "metadata": {}, "output_type": "execute_result"}], "source": ["exe = oinf.run({'X': X_test}, node_time=True)\n", "exe[1]"]}, {"cell_type": "code", "execution_count": 9, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " i \n", " name \n", " op_type \n", " time \n", " \n", " \n", " \n", " \n", " 0 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.000157 \n", " \n", " \n", " 1 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000054 \n", " \n", " \n", " 2 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000012 \n", " \n", " \n", " 3 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000019 \n", " \n", " \n", "
\n", "
"], "text/plain": [" i name op_type time\n", "0 0 LinearClassifier LinearClassifier 0.000157\n", "1 1 Normalizer Normalizer 0.000054\n", "2 2 Cast Cast 0.000012\n", "3 3 ZipMap ZipMap 0.000019"]}, "execution_count": 10, "metadata": {}, "output_type": "execute_result"}], "source": ["import pandas\n", "pandas.DataFrame(exe[1])"]}, {"cell_type": "markdown", "metadata": {}, "source": ["## Logistic regression: python runtime vs onnxruntime\n", "\n", "Function [enumerate_validated_operator_opsets](http://www.xavierdupre.fr/app/mlprodict/helpsphinx/mlprodict/onnxrt/validate/validate.html?highlight=enumerate_validated_operator_opsets#mlprodict.onnxrt.validate.validate.enumerate_validated_operator_opsets) implements automated tests for every model with artificial data. Option ``node_time`` automatically returns the time spent in each node and does it multiple time."]}, {"cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [{"name": "stderr", "output_type": "stream", "text": ["C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n"]}], "source": ["from mlprodict.onnxrt.validate import enumerate_validated_operator_opsets\n", "res = list(enumerate_validated_operator_opsets(\n", " verbose=0, models={\"LogisticRegression\"}, opset_min=12,\n", " runtime='python', debug=False, node_time=True,\n", " filter_exp=lambda m, p: p == \"b-cl\"))"]}, {"cell_type": "code", "execution_count": 11, "metadata": {"scrolled": false}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " i \n", " name \n", " op_type \n", " time \n", " N \n", " max_time \n", " min_time \n", " repeat \n", " number \n", " step \n", " \n", " \n", " \n", " \n", " 0 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.000018 \n", " 1 \n", " 0.000033 \n", " 0.000015 \n", " 20 \n", " 30 \n", " 0-LinearClassifier \n", " \n", " \n", " 1 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000017 \n", " 1 \n", " 0.000069 \n", " 0.000012 \n", " 20 \n", " 30 \n", " 1-Normalizer \n", " \n", " \n", " 2 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000004 \n", " 1 \n", " 0.000009 \n", " 0.000003 \n", " 20 \n", " 30 \n", " 2-Cast \n", " \n", " \n", " 3 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000005 \n", " 1 \n", " 0.000007 \n", " 0.000004 \n", " 20 \n", " 30 \n", " 3-ZipMap \n", " \n", " \n", " 4 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.000020 \n", " 10 \n", " 0.000052 \n", " 0.000017 \n", " 20 \n", " 20 \n", " 0-LinearClassifier \n", " \n", " \n", " 5 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000015 \n", " 10 \n", " 0.000035 \n", " 0.000013 \n", " 20 \n", " 20 \n", " 1-Normalizer \n", " \n", " \n", " 6 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000004 \n", " 10 \n", " 0.000013 \n", " 0.000003 \n", " 20 \n", " 20 \n", " 2-Cast \n", " \n", " \n", " 7 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000004 \n", " 10 \n", " 0.000008 \n", " 0.000004 \n", " 20 \n", " 20 \n", " 3-ZipMap \n", " \n", " \n", " 8 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.000024 \n", " 100 \n", " 0.000036 \n", " 0.000019 \n", " 10 \n", " 8 \n", " 0-LinearClassifier \n", " \n", " \n", " 9 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000018 \n", " 100 \n", " 0.000023 \n", " 0.000015 \n", " 10 \n", " 8 \n", " 1-Normalizer \n", " \n", " \n", " 10 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000004 \n", " 100 \n", " 0.000006 \n", " 0.000003 \n", " 10 \n", " 8 \n", " 2-Cast \n", " \n", " \n", " 11 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000007 \n", " 100 \n", " 0.000005 \n", " 0.000004 \n", " 10 \n", " 8 \n", " 3-ZipMap \n", " \n", " \n", " 12 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.000051 \n", " 1000 \n", " 0.000057 \n", " 0.000047 \n", " 5 \n", " 5 \n", " 0-LinearClassifier \n", " \n", " \n", " 13 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000041 \n", " 1000 \n", " 0.000045 \n", " 0.000040 \n", " 5 \n", " 5 \n", " 1-Normalizer \n", " \n", " \n", " 14 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000003 \n", " 1000 \n", " 0.000004 \n", " 0.000003 \n", " 5 \n", " 5 \n", " 2-Cast \n", " \n", " \n", " 15 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000004 \n", " 1000 \n", " 0.000004 \n", " 0.000004 \n", " 5 \n", " 5 \n", " 3-ZipMap \n", " \n", " \n", " 16 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.000315 \n", " 10000 \n", " 0.000328 \n", " 0.000315 \n", " 3 \n", " 3 \n", " 0-LinearClassifier \n", " \n", " \n", " 17 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.000272 \n", " 10000 \n", " 0.000284 \n", " 0.000256 \n", " 3 \n", " 3 \n", " 1-Normalizer \n", " \n", " \n", " 18 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000004 \n", " 10000 \n", " 0.000004 \n", " 0.000004 \n", " 3 \n", " 3 \n", " 2-Cast \n", " \n", " \n", " 19 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000004 \n", " 10000 \n", " 0.000004 \n", " 0.000004 \n", " 3 \n", " 3 \n", " 3-ZipMap \n", " \n", " \n", " 20 \n", " 0 \n", " LinearClassifier \n", " LinearClassifier \n", " 0.005634 \n", " 100000 \n", " 0.005634 \n", " 0.005634 \n", " 1 \n", " 2 \n", " 0-LinearClassifier \n", " \n", " \n", " 21 \n", " 1 \n", " Normalizer \n", " Normalizer \n", " 0.004671 \n", " 100000 \n", " 0.004671 \n", " 0.004671 \n", " 1 \n", " 2 \n", " 1-Normalizer \n", " \n", " \n", " 22 \n", " 2 \n", " Cast \n", " Cast \n", " 0.000024 \n", " 100000 \n", " 0.000024 \n", " 0.000024 \n", " 1 \n", " 2 \n", " 2-Cast \n", " \n", " \n", " 23 \n", " 3 \n", " ZipMap \n", " ZipMap \n", " 0.000013 \n", " 100000 \n", " 0.000013 \n", " 0.000013 \n", " 1 \n", " 2 \n", " 3-ZipMap \n", " \n", " \n", "
\n", "
"], "text/plain": [" i name op_type time N max_time \\\n", "0 0 LinearClassifier LinearClassifier 0.000018 1 0.000033 \n", "1 1 Normalizer Normalizer 0.000017 1 0.000069 \n", "2 2 Cast Cast 0.000004 1 0.000009 \n", "3 3 ZipMap ZipMap 0.000005 1 0.000007 \n", "4 0 LinearClassifier LinearClassifier 0.000020 10 0.000052 \n", "5 1 Normalizer Normalizer 0.000015 10 0.000035 \n", "6 2 Cast Cast 0.000004 10 0.000013 \n", "7 3 ZipMap ZipMap 0.000004 10 0.000008 \n", "8 0 LinearClassifier LinearClassifier 0.000024 100 0.000036 \n", "9 1 Normalizer Normalizer 0.000018 100 0.000023 \n", "10 2 Cast Cast 0.000004 100 0.000006 \n", "11 3 ZipMap ZipMap 0.000007 100 0.000005 \n", "12 0 LinearClassifier LinearClassifier 0.000051 1000 0.000057 \n", "13 1 Normalizer Normalizer 0.000041 1000 0.000045 \n", "14 2 Cast Cast 0.000003 1000 0.000004 \n", "15 3 ZipMap ZipMap 0.000004 1000 0.000004 \n", "16 0 LinearClassifier LinearClassifier 0.000315 10000 0.000328 \n", "17 1 Normalizer Normalizer 0.000272 10000 0.000284 \n", "18 2 Cast Cast 0.000004 10000 0.000004 \n", "19 3 ZipMap ZipMap 0.000004 10000 0.000004 \n", "20 0 LinearClassifier LinearClassifier 0.005634 100000 0.005634 \n", "21 1 Normalizer Normalizer 0.004671 100000 0.004671 \n", "22 2 Cast Cast 0.000024 100000 0.000024 \n", "23 3 ZipMap ZipMap 0.000013 100000 0.000013 \n", "\n", " min_time repeat number step \n", "0 0.000015 20 30 0-LinearClassifier \n", "1 0.000012 20 30 1-Normalizer \n", "2 0.000003 20 30 2-Cast \n", "3 0.000004 20 30 3-ZipMap \n", "4 0.000017 20 20 0-LinearClassifier \n", "5 0.000013 20 20 1-Normalizer \n", "6 0.000003 20 20 2-Cast \n", "7 0.000004 20 20 3-ZipMap \n", "8 0.000019 10 8 0-LinearClassifier \n", "9 0.000015 10 8 1-Normalizer \n", "10 0.000003 10 8 2-Cast \n", "11 0.000004 10 8 3-ZipMap \n", "12 0.000047 5 5 0-LinearClassifier \n", "13 0.000040 5 5 1-Normalizer \n", "14 0.000003 5 5 2-Cast \n", "15 0.000004 5 5 3-ZipMap \n", "16 0.000315 3 3 0-LinearClassifier \n", "17 0.000256 3 3 1-Normalizer \n", "18 0.000004 3 3 2-Cast \n", "19 0.000004 3 3 3-ZipMap \n", "20 0.005634 1 2 0-LinearClassifier \n", "21 0.004671 1 2 1-Normalizer \n", "22 0.000024 1 2 2-Cast \n", "23 0.000013 1 2 3-ZipMap "]}, "execution_count": 12, "metadata": {}, "output_type": "execute_result"}], "source": ["import pandas\n", "df = pandas.DataFrame(res[0]['bench-batch'])\n", "df['step'] = df.apply(lambda row: '{}-{}'.format(row['i'], row[\"name\"]), axis=1)\n", "df"]}, {"cell_type": "markdown", "metadata": {}, "source": ["Following tables shows the time spent in each node, it is relative to the total time. For one observation, the runtime spends 10% of the time in ZipMap, it is only 1% or 2% with 10 observations. These proportions change due to the computing cost of each node."]}, {"cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " N \n", " 1 \n", " 10 \n", " 100 \n", " 1000 \n", " 10000 \n", " 100000 \n", " \n", " \n", " step \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " 0-LinearClassifier \n", " 0.410138 \n", " 0.459103 \n", " 0.450882 \n", " 0.512622 \n", " 0.530490 \n", " 0.544785 \n", " \n", " \n", " 1-Normalizer \n", " 0.390060 \n", " 0.353622 \n", " 0.350126 \n", " 0.414227 \n", " 0.456671 \n", " 0.451642 \n", " \n", " \n", " 2-Cast \n", " 0.095729 \n", " 0.089857 \n", " 0.074343 \n", " 0.034398 \n", " 0.006092 \n", " 0.002306 \n", " \n", " \n", " 3-ZipMap \n", " 0.104073 \n", " 0.097418 \n", " 0.124649 \n", " 0.038753 \n", " 0.006747 \n", " 0.001267 \n", " \n", " \n", "
\n", "
"], "text/plain": ["N 1 10 100 1000 10000 100000\n", "step \n", "0-LinearClassifier 0.410138 0.459103 0.450882 0.512622 0.530490 0.544785\n", "1-Normalizer 0.390060 0.353622 0.350126 0.414227 0.456671 0.451642\n", "2-Cast 0.095729 0.089857 0.074343 0.034398 0.006092 0.002306\n", "3-ZipMap 0.104073 0.097418 0.124649 0.038753 0.006747 0.001267"]}, "execution_count": 13, "metadata": {}, "output_type": "execute_result"}], "source": ["piv = df.pivot('step', 'N', 'time')\n", "total = piv.sum(axis=0)\n", "piv / total"]}, {"cell_type": "markdown", "metadata": {}, "source": ["The python implementation of *ZipMap* does not change the data but wraps in into a frozen class [ArrayZipMapDitionary](https://github.com/sdpython/mlprodict/blob/master/mlprodict/onnxrt/ops_cpu/op_zipmap.py#L90) which mocks a list of dictionaries *pandas* can ingest to create a DataFrame. The cost is a fixed cost and does not depend on the number of processed rows."]}, {"cell_type": "code", "execution_count": 13, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["\n", " _ ._ __/__ _ _ _ _ _/_ Recorded: 00:28:08 Samples: 4\n", " /_//_/// /_\\ / //_// / //_'/ // Duration: 0.009 CPU time: 0.031\n", "/ _/ v3.0.1\n", "\n", "Program: c:\\python372_x64\\lib\\site-packages\\ipykernel_launcher.py -f C:\\Users\\xavie\\AppData\\Roaming\\jupyter\\runtime\\kernel-287476aa-b8ba-4140-902a-b0aad833ffd0.json\n", "\n", "0.008 profile pyquickhelper\\pycode\\profiling.py:49\n", "`- 0.008 :3\n", " `- 0.008 run mlprodict\\onnxrt\\onnx_inference.py:475\n", " `- 0.008 _run_sequence_runtime mlprodict\\onnxrt\\onnx_inference.py:558\n", " `- 0.008 run mlprodict\\onnxrt\\onnx_inference_node.py:141\n", " |- 0.005 run mlprodict\\onnxrt\\ops_cpu\\_op.py:417\n", " | `- 0.005 run mlprodict\\onnxrt\\ops_cpu\\_op.py:298\n", " | `- 0.005 _run mlprodict\\onnxrt\\ops_cpu\\op_linear_classifier.py:40\n", " | |- 0.003 [self] \n", " | `- 0.002 argmax <__array_function__ internals>:2\n", " | `- 0.002 argmax numpy\\core\\fromnumeric.py:1112\n", " | [3 frames hidden] numpy\n", " | 0.002 _wrapfunc numpy\\core\\fromnumeric.py:55\n", " `- 0.003 run mlprodict\\onnxrt\\ops_cpu\\_op.py:383\n", " `- 0.003 run mlprodict\\onnxrt\\ops_cpu\\_op.py:298\n", " `- 0.003 _run mlprodict\\onnxrt\\ops_cpu\\op_normalizer.py:66\n", " `- 0.003 norm_l1 mlprodict\\onnxrt\\ops_cpu\\op_normalizer.py:42\n", " `- 0.003 _norm_L1_inplace mlprodict\\onnxrt\\ops_cpu\\op_normalizer.py:49\n", " |- 0.002 [self] \n", " `- 0.002 _sum numpy\\core\\_methods.py:36\n", " [2 frames hidden] numpy\n", "\n", "\n"]}], "source": ["from pyquickhelper.pycode.profiling import profile\n", "bigX = numpy.random.randn(100000, X_test.shape[1]).astype(numpy.float32)\n", "print(profile(lambda: oinf.run({'X': bigX}), pyinst_format=\"text\")[1])"]}, {"cell_type": "markdown", "metadata": {}, "source": ["The class *ArrayZipMapDictionary* is fast to build but has an overhead after that because it builds data when needed."]}, {"cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [{"data": {"text/plain": ["mlprodict.onnxrt.ops_cpu.op_zipmap.ArrayZipMapDictionary"]}, "execution_count": 15, "metadata": {}, "output_type": "execute_result"}], "source": ["res = oinf.run({'X': bigX})\n", "prob = res['output_probability']\n", "type(prob)"]}, {"cell_type": "code", "execution_count": 15, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["721 ms \u00b1 54.5 ms per loop (mean \u00b1 std. dev. of 7 runs, 1 loop each)\n"]}], "source": ["%timeit pandas.DataFrame(prob)"]}, {"cell_type": "code", "execution_count": 16, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["108 ms \u00b1 2.01 ms per loop (mean \u00b1 std. dev. of 7 runs, 10 loops each)\n"]}], "source": ["list_of_dict = [v.asdict() for v in prob]\n", "%timeit pandas.DataFrame(list_of_dict)"]}, {"cell_type": "markdown", "metadata": {}, "source": ["But if you just need to do the following:"]}, {"cell_type": "code", "execution_count": 17, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["713 ms \u00b1 56.6 ms per loop (mean \u00b1 std. dev. of 7 runs, 1 loop each)\n"]}], "source": ["%timeit pandas.DataFrame(prob).values"]}, {"cell_type": "markdown", "metadata": {}, "source": ["Then, you can just do that:"]}, {"cell_type": "code", "execution_count": 18, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["[0, 1, 2]\n", "390 ns \u00b1 51.2 ns per loop (mean \u00b1 std. dev. of 7 runs, 1000000 loops each)\n"]}], "source": ["print(prob.columns)\n", "%timeit prob.values"]}, {"cell_type": "markdown", "metadata": {}, "source": ["And then:\n"]}, {"cell_type": "code", "execution_count": 19, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["215 \u00b5s \u00b1 82.6 \u00b5s per loop (mean \u00b1 std. dev. of 7 runs, 100 loops each)\n"]}], "source": ["%timeit -n 100 pandas.DataFrame(prob.values, columns=prob.columns)"]}, {"cell_type": "markdown", "metadata": {}, "source": ["We can then compare to what *onnxruntime* would do when the runtime is called indenpently for each node. We use the runtime named [onnxruntime2](http://www.xavierdupre.fr/app/mlprodict/helpsphinx/onnx_runtime.html?highlight=onnxruntime2#onnxruntime2-independent-onnxruntime-for-every-node). Class *OnnxInference* splits the ONNX graph into multiple ONNX graphs, one for each node, and then calls *onnxruntime* for each of them indenpently. *Python* handles the graph logic."]}, {"cell_type": "code", "execution_count": 20, "metadata": {"scrolled": false}, "outputs": [{"name": "stderr", "output_type": "stream", "text": ["C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\linear_model\\_logistic.py:1356: UserWarning: 'n_jobs' > 1 does not have any effect when 'solver' is set to 'liblinear'. Got 'n_jobs' = 4.\n", " \" = {}.\".format(effective_n_jobs(self.n_jobs)))\n"]}], "source": ["res = list(enumerate_validated_operator_opsets(\n", " verbose=0, models={\"LogisticRegression\"}, opset_min=12,\n", " runtime='onnxruntime2', debug=False, node_time=True))"]}, {"cell_type": "code", "execution_count": 21, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["0 Unable to load node 'ZipMap' (output type was inferred)\n", "1 Unable to load node 'ZipMap' (output type was inferred)\n", "4 Unable to load node 'LinearClassifier' (output type was guessed)\n", "5 Unable to load node 'LinearClassifier' (output type was guessed)\n", "6 Unable to load node 'LinearClassifier' (output type was guessed)\n", "7 Unable to load node 'LinearClassifier' (output type was guessed)\n", "8 Unable to load node 'ZipMap' (output type was inferred)\n", "9 Unable to load node 'ZipMap' (output type was inferred)\n"]}], "source": ["res0 = None\n", "for i, r in enumerate(res):\n", " if \"available-ERROR\" in r:\n", " print(i, str(r['available-ERROR']).split(\"\\n\")[0])\n", " elif res0 is None:\n", " res0 = r"]}, {"cell_type": "code", "execution_count": 22, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": [" i name op_type time N max_time \\\n", "0 0 LinearClassifier LinearClassifier 0.000052 1 0.000190 \n", "1 0 LinearClassifier LinearClassifier 0.000044 10 0.000070 \n", "2 0 LinearClassifier LinearClassifier 0.000071 100 0.000133 \n", "3 0 LinearClassifier LinearClassifier 0.000066 1000 0.000079 \n", "4 0 LinearClassifier LinearClassifier 0.000409 10000 0.000408 \n", "5 0 LinearClassifier LinearClassifier 0.003275 100000 0.003275 \n", "\n", " min_time repeat number \n", "0 0.000028 20 30 \n", "1 0.000031 20 20 \n", "2 0.000046 10 8 \n", "3 0.000057 5 5 \n", "4 0.000365 3 3 \n", "5 0.003275 1 2 \n"]}, {"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " N \n", " 1 \n", " 10 \n", " 100 \n", " 1000 \n", " 10000 \n", " 100000 \n", " \n", " \n", " step \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " 0-LinearClassifier \n", " 1.0 \n", " 1.0 \n", " 1.0 \n", " 1.0 \n", " 1.0 \n", " 1.0 \n", " \n", " \n", "
\n", "
"], "text/plain": ["N 1 10 100 1000 10000 100000\n", "step \n", "0-LinearClassifier 1.0 1.0 1.0 1.0 1.0 1.0"]}, "execution_count": 23, "metadata": {}, "output_type": "execute_result"}], "source": ["if '_6ort_run_batch_exc' in res[0]:\n", " m = \"Something went wrong.\", res[0]['_6ort_run_batch_exc']\n", "else:\n", " df = pandas.DataFrame(res0['bench-batch'])\n", " print(df)\n", " df['step'] = df.apply(lambda row: '{}-{}'.format(row['i'], row[\"name\"]), axis=1)\n", " piv = df.pivot('step', 'N', 'time')\n", " total = piv.sum(axis=0)\n", " m = piv / total\n", "m"]}, {"cell_type": "markdown", "metadata": {}, "source": ["*onnxruntime* creates a new container each time a ZipMap is executed. That's whay it takes that much time and the ratio increases when the number of observations increases."]}, {"cell_type": "markdown", "metadata": {}, "source": ["## GaussianProcessRegressor\n", "\n", "This operator is slow for small batches compare to scikit-learn but closes the gap as the batch size increases. Let\u2019s see where the time goes."]}, {"cell_type": "code", "execution_count": 23, "metadata": {}, "outputs": [{"data": {"text/plain": ["(12, 12)"]}, "execution_count": 24, "metadata": {}, "output_type": "execute_result"}], "source": ["from onnx.defs import onnx_opset_version\n", "from mlprodict.tools.asv_options_helper import get_opset_number_from_onnx\n", "onnx_opset_version(), get_opset_number_from_onnx()"]}, {"cell_type": "code", "execution_count": 24, "metadata": {"scrolled": false}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["[enumerate_validated_operator_opsets] opset in [12, 12].\n"]}, {"name": "stderr", "output_type": "stream", "text": ["GaussianProcessRegressor : 0%| | 0/1 [00:00, ?it/s]"]}, {"name": "stdout", "output_type": "stream", "text": ["[enumerate_compatible_opset] opset in [12, 12].\n"]}, {"name": "stderr", "output_type": "stream", "text": ["GaussianProcessRegressor : 100%|\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588| 1/1 [00:05<00:00, 5.66s/it]\n"]}], "source": ["res = list(enumerate_validated_operator_opsets(\n", " verbose=1, models={\"GaussianProcessRegressor\"},\n", " opset_min=get_opset_number_from_onnx(),\n", " opset_max=get_opset_number_from_onnx(),\n", " runtime='python', debug=False, node_time=True,\n", " filter_exp=lambda m, p: p == \"b-reg\"))"]}, {"cell_type": "code", "execution_count": 25, "metadata": {}, "outputs": [], "source": ["res0 = None\n", "for i, r in enumerate(res):\n", " if \"available-ERROR\" in r:\n", " print(i, str(r['available-ERROR']).split(\"\\n\")[0])\n", " elif res0 is None:\n", " res0 = r"]}, {"cell_type": "code", "execution_count": 26, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " i \n", " name \n", " op_type \n", " time \n", " N \n", " max_time \n", " min_time \n", " repeat \n", " number \n", " step \n", " \n", " \n", " \n", " \n", " 0 \n", " 0 \n", " kgpd_CDist \n", " CDist \n", " 0.000033 \n", " 1 \n", " 0.000045 \n", " 0.000027 \n", " 20 \n", " 30 \n", " 00-kgpd_CDist \n", " \n", " \n", " 1 \n", " 1 \n", " kgpd_Div \n", " Div \n", " 0.000009 \n", " 1 \n", " 0.000016 \n", " 0.000007 \n", " 20 \n", " 30 \n", " 01-kgpd_Div \n", " \n", " \n", " 2 \n", " 2 \n", " kgpd_Mul \n", " Mul \n", " 0.000006 \n", " 1 \n", " 0.000007 \n", " 0.000005 \n", " 20 \n", " 30 \n", " 02-kgpd_Mul \n", " \n", " \n", " 3 \n", " 3 \n", " kgpd_Sin \n", " Sin \n", " 0.000007 \n", " 1 \n", " 0.000009 \n", " 0.000006 \n", " 20 \n", " 30 \n", " 03-kgpd_Sin \n", " \n", " \n", " 4 \n", " 4 \n", " kgpd_Div1 \n", " Div \n", " 0.000007 \n", " 1 \n", " 0.000008 \n", " 0.000005 \n", " 20 \n", " 30 \n", " 04-kgpd_Div1 \n", " \n", " \n", "
\n", "
"], "text/plain": [" i name op_type time N max_time min_time repeat number \\\n", "0 0 kgpd_CDist CDist 0.000033 1 0.000045 0.000027 20 30 \n", "1 1 kgpd_Div Div 0.000009 1 0.000016 0.000007 20 30 \n", "2 2 kgpd_Mul Mul 0.000006 1 0.000007 0.000005 20 30 \n", "3 3 kgpd_Sin Sin 0.000007 1 0.000009 0.000006 20 30 \n", "4 4 kgpd_Div1 Div 0.000007 1 0.000008 0.000005 20 30 \n", "\n", " step \n", "0 00-kgpd_CDist \n", "1 01-kgpd_Div \n", "2 02-kgpd_Mul \n", "3 03-kgpd_Sin \n", "4 04-kgpd_Div1 "]}, "execution_count": 27, "metadata": {}, "output_type": "execute_result"}], "source": ["df = pandas.DataFrame(res0['bench-batch'])\n", "df['step'] = df.apply(lambda row: '{0:02d}-{1}'.format(row['i'], row[\"name\"]), axis=1)\n", "df.head()"]}, {"cell_type": "code", "execution_count": 27, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " N \n", " 1 \n", " 10 \n", " 100 \n", " 1000 \n", " 10000 \n", " 100000 \n", " \n", " \n", " step \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " 00-kgpd_CDist \n", " 0.311496 \n", " 0.300665 \n", " 0.244035 \n", " 0.227984 \n", " 0.264447 \n", " 0.288546 \n", " \n", " \n", " 01-kgpd_Div \n", " 0.082535 \n", " 0.067193 \n", " 0.028348 \n", " 0.011667 \n", " 0.012230 \n", " 0.015447 \n", " \n", " \n", " 02-kgpd_Mul \n", " 0.059840 \n", " 0.050664 \n", " 0.018670 \n", " 0.006959 \n", " 0.010950 \n", " 0.012468 \n", " \n", " \n", " 03-kgpd_Sin \n", " 0.067037 \n", " 0.086529 \n", " 0.106165 \n", " 0.113068 \n", " 0.102102 \n", " 0.107563 \n", " \n", " \n", " 04-kgpd_Div1 \n", " 0.061852 \n", " 0.053088 \n", " 0.025749 \n", " 0.010935 \n", " 0.009810 \n", " 0.009875 \n", " \n", " \n", " 05-kgpd_Pow \n", " 0.072520 \n", " 0.166539 \n", " 0.361318 \n", " 0.438253 \n", " 0.418169 \n", " 0.404182 \n", " \n", " \n", " 06-kgpd_Mul1 \n", " 0.057508 \n", " 0.050477 \n", " 0.020386 \n", " 0.010334 \n", " 0.009079 \n", " 0.010466 \n", " \n", " \n", " 07-kgpd_Exp \n", " 0.067885 \n", " 0.098850 \n", " 0.150876 \n", " 0.168079 \n", " 0.165177 \n", " 0.145106 \n", " \n", " \n", " 08-gpr_MatMul \n", " 0.137546 \n", " 0.064570 \n", " 0.025069 \n", " 0.009029 \n", " 0.007134 \n", " 0.006159 \n", " \n", " \n", " 09-gpr_Add \n", " 0.081782 \n", " 0.061424 \n", " 0.019383 \n", " 0.003692 \n", " 0.000903 \n", " 0.000190 \n", " \n", " \n", "
\n", "
"], "text/plain": ["N 1 10 100 1000 10000 100000\n", "step \n", "00-kgpd_CDist 0.311496 0.300665 0.244035 0.227984 0.264447 0.288546\n", "01-kgpd_Div 0.082535 0.067193 0.028348 0.011667 0.012230 0.015447\n", "02-kgpd_Mul 0.059840 0.050664 0.018670 0.006959 0.010950 0.012468\n", "03-kgpd_Sin 0.067037 0.086529 0.106165 0.113068 0.102102 0.107563\n", "04-kgpd_Div1 0.061852 0.053088 0.025749 0.010935 0.009810 0.009875\n", "05-kgpd_Pow 0.072520 0.166539 0.361318 0.438253 0.418169 0.404182\n", "06-kgpd_Mul1 0.057508 0.050477 0.020386 0.010334 0.009079 0.010466\n", "07-kgpd_Exp 0.067885 0.098850 0.150876 0.168079 0.165177 0.145106\n", "08-gpr_MatMul 0.137546 0.064570 0.025069 0.009029 0.007134 0.006159\n", "09-gpr_Add 0.081782 0.061424 0.019383 0.003692 0.000903 0.000190"]}, "execution_count": 28, "metadata": {}, "output_type": "execute_result"}], "source": ["pivpy = df.pivot('step', 'N', 'time')\n", "total = pivpy.sum(axis=0)\n", "pivpy / total"]}, {"cell_type": "code", "execution_count": 28, "metadata": {}, "outputs": [{"data": {"image/png": "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H2XzUIQQQgghhOgwJMicoqVLl1JUVMT777/P+vXr+cY3vkFRURHLly9n+fLlHDp0iLlz5/LGG2+wZs0aRo0axaOPPprYvlOnTqxcuZKvf/3rfOMb38jegQghhBBCCNGBSJA5RcOHD+eNN97g3nvv5a9//SudO3dOWf/222+zceNGPvnJT1JeXs4zzzzDP//5z8T6a6+9NvH8j3/847S2XQghhBBCiI6qXd1HpiM6//zzWb16Na+99hrf+c53+MxnPpOyXmvN5ZdfzuLFizNun3zFL7n6lxBCCCGEEM0jPTKnaO/eveTm5vKlL32Je+65hzVr1lBQUEBlZSUAF198MX//+98T57/U1NSwZcuWxPbPPfdc4vkTn/jE6T8AIYQQQgghOiDpkTlFH3zwAd/61rcwDAOfz8djjz3GP/7xD6644gp69+7N8uXLWbBgAddeey3hcBiAuXPncv755wMQDocZO3YsjuM02GsjhBBCCCGESKW01lnZ8ahRo/SqVatSlm3atInBgwdnpT3Z0K9fP1atWkVhYWG2m3LKzrb3TgghhBBCtD2l1Gqt9ahM62RomRBCCCGEEKLDkaFlWbRz585sN0EIIYQQQogOSXpkhBBCCCGEEB2OBBkhhBBCCCFEhyNBRgghhBBCCNHhSJARQgghhBBCdDgSZIQQQgghhBAdjgSZDJYuXcqgQYMYMGAADz/8MABHjhzh8ssvZ+DAgVx++eUcPXo047YTJkwg/f44raGpequqqrjllls477zzGDp0KOPGjeOdd94BwDRNysvLGTp0KCNGjODRRx/FcRwAVq1axR133NFgvTt37uTZZ59t3YMRQgghhBDiFEmQSROLxbj99tt5/fXX2bhxI4sXL2bjxo08/PDDfPrTn2br1q18+tOfTgSc9uLmm2+mW7dubN26lQ0bNrBgwQIOHToEQE5ODmvXrmXDhg0sW7aM1157jR/84AcAjBo1ip///OcN1itBRgghhBBCtEft9j4yP/j9BjbuPdGqdQ4p6sT3Pz+00TIrV65kwIABlJaWAjBz5kxefvllXn75Zd58800AbrzxRiZMmMAjjzzSYD2O41BRUUFJSQlz587lySef5JFHHqGoqIiBAwcSCASYP38+s2bNIhgMsmHDBvbv38+jjz7KlClTqK2tpaKigo0bNzJ48GBqa2sb3Ne2bdt45513WLRo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\n", "text/plain": [""]}, "metadata": {"needs_background": "light"}, "output_type": "display_data"}], "source": ["ax = (pivpy / total).T.plot(logx=True, figsize=(14, 4))\n", "ax.set_ylim([0,1])\n", "ax.set_title(\"Time spent in each node relatively to the total time\\npython runtime\");"]}, {"cell_type": "markdown", "metadata": {}, "source": ["The operator *Scan* is clearly time consuming when the batch size is small. *onnxruntime* is more efficient for this one."]}, {"cell_type": "code", "execution_count": 29, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["[enumerate_validated_operator_opsets] opset in [12, 12].\n"]}, {"name": "stderr", "output_type": "stream", "text": ["GaussianProcessRegressor : 0%| | 0/1 [00:00, ?it/s]"]}, {"name": "stdout", "output_type": "stream", "text": ["[enumerate_compatible_opset] opset in [12, 12].\n"]}, {"name": "stderr", "output_type": "stream", "text": ["GaussianProcessRegressor : 100%|\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588| 1/1 [00:06<00:00, 6.84s/it]\n"]}], "source": ["res = list(enumerate_validated_operator_opsets(\n", " verbose=1, models={\"GaussianProcessRegressor\"}, \n", " opset_min=get_opset_number_from_onnx(),\n", " opset_max=get_opset_number_from_onnx(),\n", " runtime='onnxruntime2', debug=False, node_time=True,\n", " filter_exp=lambda m, p: p == \"b-reg\"))"]}, {"cell_type": "code", "execution_count": 30, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " N \n", " 1 \n", " 10 \n", " 100 \n", " 1000 \n", " 10000 \n", " 100000 \n", " \n", " \n", " step \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " 00-kgpd_CDist \n", " 0.114001 \n", " 0.120884 \n", " 0.128845 \n", " 0.148042 \n", " 0.156776 \n", " 0.180377 \n", " \n", " \n", " 01-kgpd_Div \n", " 0.101792 \n", " 0.098622 \n", " 0.085983 \n", " 0.085108 \n", " 0.086603 \n", " 0.084520 \n", " \n", " \n", " 02-kgpd_Mul \n", " 0.099980 \n", " 0.097547 \n", " 0.084001 \n", " 0.064706 \n", " 0.072849 \n", " 0.081023 \n", " \n", " \n", " 03-kgpd_Sin \n", " 0.089632 \n", " 0.103505 \n", " 0.194194 \n", " 0.301002 \n", " 0.245769 \n", " 0.260717 \n", " \n", " \n", " 04-kgpd_Div1 \n", " 0.099119 \n", " 0.096737 \n", " 0.088709 \n", " 0.063237 \n", " 0.095840 \n", " 0.091635 \n", " \n", " \n", " 05-kgpd_Pow \n", " 0.108045 \n", " 0.098307 \n", " 0.081161 \n", " 0.064898 \n", " 0.079015 \n", " 0.076962 \n", " \n", " \n", " 06-kgpd_Mul1 \n", " 0.098561 \n", " 0.098475 \n", " 0.082770 \n", " 0.063557 \n", " 0.087732 \n", " 0.076762 \n", " \n", " \n", " 07-kgpd_Exp \n", " 0.090019 \n", " 0.087015 \n", " 0.086282 \n", " 0.088542 \n", " 0.103798 \n", " 0.087690 \n", " \n", " \n", " 08-gpr_MatMul \n", " 0.100426 \n", " 0.102766 \n", " 0.106220 \n", " 0.102751 \n", " 0.069157 \n", " 0.059617 \n", " \n", " \n", " 09-gpr_Add \n", " 0.098425 \n", " 0.096143 \n", " 0.061836 \n", " 0.018155 \n", " 0.002462 \n", " 0.000696 \n", " \n", " \n", "
\n", "
"], "text/plain": ["N 1 10 100 1000 10000 100000\n", "step \n", "00-kgpd_CDist 0.114001 0.120884 0.128845 0.148042 0.156776 0.180377\n", "01-kgpd_Div 0.101792 0.098622 0.085983 0.085108 0.086603 0.084520\n", "02-kgpd_Mul 0.099980 0.097547 0.084001 0.064706 0.072849 0.081023\n", "03-kgpd_Sin 0.089632 0.103505 0.194194 0.301002 0.245769 0.260717\n", "04-kgpd_Div1 0.099119 0.096737 0.088709 0.063237 0.095840 0.091635\n", "05-kgpd_Pow 0.108045 0.098307 0.081161 0.064898 0.079015 0.076962\n", "06-kgpd_Mul1 0.098561 0.098475 0.082770 0.063557 0.087732 0.076762\n", "07-kgpd_Exp 0.090019 0.087015 0.086282 0.088542 0.103798 0.087690\n", "08-gpr_MatMul 0.100426 0.102766 0.106220 0.102751 0.069157 0.059617\n", "09-gpr_Add 0.098425 0.096143 0.061836 0.018155 0.002462 0.000696"]}, "execution_count": 31, "metadata": {}, "output_type": "execute_result"}], "source": ["try:\n", " df = pandas.DataFrame(res[0]['bench-batch'])\n", "except KeyError as e:\n", " print(\"No model available.\")\n", " r, df = None, None\n", "if df is not None:\n", " df['step'] = df.apply(lambda row: '{0:02d}-{1}'.format(row['i'], row[\"name\"]), axis=1)\n", " pivort = df.pivot('step', 'N', 'time')\n", " total = pivort.sum(axis=0)\n", " r = pivort / total\n", "r"]}, {"cell_type": "code", "execution_count": 31, "metadata": {}, "outputs": [{"data": {"image/png": "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+MnfAaWUUkoppVogbZE5Tm+++Sbf/va3sSyLaDTKww8/zN///ncuv/xyzjvvPJYtW8bcuXO55pprqK6uBmDGjBn07t0bgOrqaoYNG4bnebW22iillFJKKaXSiTEmJxsePHiwWbVqVVrahg0b6Nu3b07qkwvdunVj1apVdOrUKddVOW6n23enlFJKKaVOPBF5zRgzONsy7VqmlFJKKaWUanG0a1kO7dixI9dVUEoppZRSqkXSFhmllFJKKaVUi6OBjFJKKaWUUqrF0UBGKaWUUkop1eJoIKOUUkoppZRqcTSQUUoppZRSSrU4GshksWTJEvr06UNpaSkzZ84E4MCBA1x22WX06tWLyy67jIMHD2Zdd+TIkWQ+H6cp1FfukSNHuPHGG+nZsyf9+/dn+PDhrFixAgDbtikvL6d///4MGjSIBx98EM/zAFi1ahW33XZbreXu2LGDX//61027M0oppZRSSh0nDWQyuK7LLbfcwosvvsj69etZsGAB69evZ+bMmXzqU59i8+bNfOpTn0oGOM3Fl770JTp06MDmzZtZt24dc+fOZf/+/QC0atWK1atXs27dOpYuXcrixYu59957ARg8eDAPPfRQreVqIKOUUkoppZqjZvscmXt/v471ez5s0jL7FZ3BDz7bv848K1eupLS0lB49egAwefJknn32WZ599llefvllAK6//npGjhzJAw88UGs5nudRUVFBSUkJM2bM4NFHH+WBBx6gqKiIXr16kZ+fz+zZs5k6dSoFBQWsW7eOffv28eCDDzJ27FgqKyupqKhg/fr19O3bl8rKylq3tXXrVlasWMH8+fOxLD827dGjR3Ifws4++2weeeQRhgwZwj333MPy5cuZNWsWzz//PMuXL+frX/86ACLCK6+8wl133cWGDRsoLy/n+uuv55vf/Gadn59SSimllFInQ7MNZHJl9+7dlJSUJOeLi4tZsWIF+/bt47zzzgPgvPPO49133621DMdxuO666xgwYADTp09nz5493Hfffbz++uu0bduWT37ykwwaNCiZf8eOHSxfvpytW7cyatQotmzZwsMPP0xhYSFr1qxhzZo1XHDBBbVub926dZSXl2PbdoP2sUePHnieV2MfZs2axc9//nM+8YlPcOTIEQoKCpg5c2Yy0FFKKaWUUqq5aLaBTH0tJyeKMaZGmog0qowbb7yRSZMmMX36dMBv5RkxYgQdOnQAYOLEiWzatCmZf9KkSViWRa9evejRowcbN27klVdeSY5dKSsro6ys7Fh3Kats+/mJT3yC22+/neuuu44rr7yS4uLiJt2mUkoppZRSTUXHyGQoLi5m586dyfldu3ZRVFTEOeecw969ewHYu3cvZ599NgAVFRWUl5czZsyY5DoXX3wxy5Yto6qqCsgeNIRlBkqJ+YYGUP379+eNN95IDuCvz7Zt27BtO7kPCXfddRe//OUvqays5KKLLmLjxo0NKk8ppZRSSqmTTQOZDEOGDGHz5s1s376dWCzGwoULGTduHOPGjeOJJ54A4IknnuBzn/scAI8//jirV69m8eLFyTJuuOEGxowZw8SJE3Ech6FDh7J8+XIOHjyI4zg888wzadtctGgRnuexdetWtm3bRp8+fRg+fDjz588HYO3ataxZs6bWOvfs2ZPBgwfzgx/8IBk0bd68mWeffbZG3vfee4+bbrqJW2+9tUagtHXrVgYOHMidd97J4MGD2bhxI23btuXw4cPH8EkqpZRSSil14jTbrmW5EolEmD17NqNHj8Z1XaZNm0b//v256667mDRpEo8++ihdunRh0aJFdZZz++23c+jQIaZMmcL8+fO5++67GTZsGEVFRfTr14927dol8/bp04cRI0awb98+5syZQ0FBATfffDMVFRWUlZVRXl7O0KFD69zeL3/5S771rW9RWlpKYWEhHTt25Mc//jEAlZWVlJeXE4/HiUQiTJkyhdtvv71GGT/96U9ZtmwZtm3Tr18/Lr/8cizLIhKJMGjQIKZOnaqD/ZVSSimlVLMg9XV7OlEGDx5sMp+LsmHDBvr27ZuT+pxoR44coU2bNjiOw4QJE5g2bRoTJkxg6tSpjB07lquuuirXVTwup/J3p5RSSimlckNEXjPGDM62TLuWnST33HMP5eXlDBgwgO7duzN+/PhcV0kppZRSSqkWS7uWnSSzZs3Kmj537txGlTNs2DCqq6vT0ubNm8fAgQOPtWpKKaWUUkq1OBrItDArVqzIdRWUUkoppZTKOe1appRSSimllGpxNJBRSimllFJKtTgayCillFJKKaVanAYFMiLyGRH5l4hsEZG7sixvJyK/F5E3RGSdiFQ0fVWVUkoppZRSyldvICMiNvBz4HKgH3CNiPTLyHYLsN4YMwgYCfxERPKauK4nzZIlS+jT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p07J+dq2O2TIEFatWkWPHj247LLL2L9/P//zP//DhRde2KjtKaWUUkoplSvatSzDkCFD2Lx5M9u3bycWi7Fw4ULGjRvH3r17k3l++9vfMmDAAAAef/xxVq9enXYXsxtuuIExY8YwceJEHMdh6NChLF++nIMHD+I4Ds8880zaNhctWoTneWzdupVt27bRp08fhg8fzvz58wFYu3Yta9asafS+hMvYtGkTb7/9Nn369CEvL4+SkhKeeuopLrroIi699FJmzZql3cqUUkoppVSLoS0yGSKRCLNnz2b06NG4rsu0adPo378/U6ZMYfXq1YgI3bp147//+7/rLOf222/n0KFDTJkyhfnz53P33XczbNgwioqK6NevH+3atUvm7dOnDyNGjGDfvn3MmTOHgoICbr75ZioqKigrK6O8vJyhQ4c2el+++tWvctNNNzFw4EAikQhz584lPz8fgEsvvZQ///nPFBYWcumll7Jr1y4NZJRSSimlVIsh9XV7OlEGDx5sMp+LsmHDBvr27ZuT+pxoR44coU2bNjiOw4QJE5g2bRoTJkxg6tSpjB07lquuuirXVTwup/J3p5RSSimlckNEXjPGDM62TLuWnST33HMP5eXlDBgwgO7duzN+/PhcV0kppZRSSqkWS7uWnSSzZs3Kmj537txGlTNs2DCqq6vT0ubNm8fAgQOPtWpKKaWUUkq1OBrItDArVqzIdRWUUkoppZTKOe1appRSSimllGpxNJBRSimllFJKtTgayCillFJKKaVaHA1klFJKKaWUUi2OBjJZLFmyhD59+lBaWsrMmTOT6f/1X/9Fnz596N+/P9/5zneyrjty5Egyn4/TFOort1u3bjUeaJm43XN9unXrxv79+wGYNm0aZ599doPWU0oppZRSKlea7V3LPvj9VmJ7jjZpmXlFrTnzsz3rzOO6LrfccgtLly6luLiYIUOGMG7cOPbt28ezzz7LmjVryM/P5913323SujWFw4cPs3PnTkpKStiwYcMxlTF16lRuvfVWvvjFLzZx7ZRSSimllGo62iKTYeXKlZSWltKjRw/y8vKYPHkyzz77LA8//DB33XUX+fn5AJx99tl1luN5Htdffz3f+973AHj00Ufp3bs3I0eO5Mtf/jK33nor4AcON910E5deeim9e/fm+eefB6CyspLJkydTVlbG1VdfTWVlZb11nzRp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Z+ta1r9/f6ZMmcJnP/tZ/v73v5OXl5dcltiPa665hm9+85v1lq+UUkoppVRzoYP9MxQXF7Nz587k/K5duygqKgL8lpbf/OY3XH311cnlFRUVlJeXM2bMmGTaxRdfzLJly6iqqgKyB0dh4UApPJ+ZfqzefPNNzjzzTPbt21frdptqW0oppZRSSp0MGshkGDJkCJs3b2b79u3EYjEWLlzIuHHjAPjTn/7E+eefT3FxcTL/448/zurVq1m8OHV36htuuIExY8YwceJEHMdh6NChLF++nIMHD+I4Ds8880zaNhctWoTneWzdupVt27bRp08fhg8fzvz58wFYu3Yta9asOab9+c1vfsP777+fbOH54IMPkssSNzB48skn+fjHP35M5SullFJKKZULzbZrWa5EIhFmz57N6NGjcV2XadOm0b9/fwAWLlxYb7eyhNtvv51Dhw4xZcoU5s+fz913382wYcMoKiqiX79+aXc969OnDyNGjGDfvn3MmTOHgoICbr75ZioqKigrK6O8vJyhQ4fWu83wGJmysjIefPBB7rrrLv785z9TUlLCrbfeyte//nWeeOIJAKqrqxk2bBie57FgwYLGflRKKaWUUkrljNTX7elEGTx4sMl8LsqGDRvo27dvTupzoh05coQ2bdrgOA4TJkxg2rRpTJgwgalTpzJ27Fiuuuqqk1qfbt26sWrVqia7XfOp/N0ppZRSSqncEJHXjDGDsy3TrmUnyT333EN5eTkDBgyge/fujB8/PtdVUkoppZRSqsXSrmUnyaxZs7Kmz507t1HlDBs2jOrq6rS0efPmMXDgwEaVs2PHjkblV0oppZRSqjnRQKaFCT8HRimllFJKqdOVdi1TSimllFJKtTgayCillFJKKaVaHO1appRSSjVjJh4ntnMniBDp0AHrjDP0IcZKKYUGMkoppVSz4FVXE9uxg+otW4ht3Ur1lq1Ub91K7K23wHFSGaNRIu3bY3foQKRDB+yOHYl0aI/doSORjh1S6R06YHfoiNW6UAMfpdQpSQOZLJYsWcLXv/51XNflS1/6EnfddRerV6/mpptuoqqqikgkwi9+8YsGPaSyqXTr1o2SkhL+8pe/JNPKy8txHIe1a9fWut6OHTv4v//7P6699loAXn75ZUaNGsUvf/lLbrjhBgD++c9/csEFF/DjH/+YO+64o9ayXn75ZWbNmsXz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7Ny5M+v6FRUVPPLII1x88cXcddddactWrlzJ2rVrKSwsZMiQIVxxxRV06tSJf/3rXzz++OP84he/qLVef/vb3+jevTs9e/Zk5MiRLF68mCuvvJLf/va3/Otf/+LNN99k37599OvXj2nTplFVVcWXv/xlXnrpJUpLS7n66qub5gNSSp107gcfBN3AtqYFLs477yTzSDRKXo8etCoro92E8akHR3bpguhDI5VSSp2CGtIiMxTYYozZBiAiC4HPAclAxhjzf6H8rwJ1N3s0QH0tJydKuEUjQUR47LHHuO222/jhD3/IuHHjyMtyYvDBBx9w+PBhLr74YgCuvfbatDEpl112GR07dgTgyiuv5K9//Svjx4+na9euXHTRRXXWa8GCBUyePBnwW4nmzZvHlVdeySuvvMI111yDbdsUFRXxyU9+EoCNGzfSvXt3evXyn7b1hS98gUceeeQYPhGl1MlgjMF9//0az1+p3roVd//+ZD5p1Yr8Hj0oHDok7Q5h0eJifWikUkqp00pD/up1BsLND7uou7XlBuDF46lULhUXF6e1tuzatYuioiLOP/98/vjHPwKwadMmXnjhBcBvgfnnP/9JUVER8+fPr7PszNuQJuZb19Mf3XVdnnnmGZ577jnuv/9+jDG8//77HA6e11Db7U31tqdKNT/GGJx9+2q0rsS2bME9dCiZz2rThryePWgzfHjoDmGlRIvOQ2oZR6eUUkqdThoSyGQ7G67ZbAGIyCj8QOaSWpZ/BfgKQJcuXRpYxZNryJAhbN68me3bt9O5c2cWLlzIr3/9a959913OPvtsPM9jxowZ3HTTTQA8/vjjaeu3bduWV199lYsuuoiFCxemLVu6dCkHDhygVatW/O53v+Oxxx5rUJ3+9Kc/MWjQIP7whz8k066//np+97vfMXz4cP77v/+bL37xi7z77rssW7aMa6+9lvPPP5/t27ezdetWevbsyYIFC47zk1FKNZTxPJx33iH29k5ib79FfOdOYm+9TWznTuJvvYUXfgZLu3bklZbSdvTo5O2M80tLiZx9tl6MUEopperQkEBmF1ASmi8G9mRmEpEy4JfA5caY97MVZIx5BH/8DIMHD84aDOVaJBJh9uzZjB49Gtd1mTZtGv379+dnP/sZP//5zwG/W1hFRUXW9R999FG+/OUv07p1a0aOHEm7du2Syy655BKmTJnC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\n", "text/plain": [""]}, "metadata": {"needs_background": "light"}, "output_type": "display_data"}], "source": ["if r is not None:\n", " ax = (pivort / total).T.plot(logx=True, figsize=(14, 4))\n", " ax.set_ylim([0,1])\n", " ax.set_title(\"Time spent in each node relatively to the total time\\nonnxtunime\");"]}, {"cell_type": "markdown", "metadata": {}, "source": ["The results are relative. Let's see which runtime is best node by node."]}, {"cell_type": "code", "execution_count": 32, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " N \n", " 1 \n", " 10 \n", " 100 \n", " 1000 \n", " 10000 \n", " 100000 \n", " \n", " \n", " step \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " 00-kgpd_CDist \n", " -0.239113 \n", " -0.367743 \n", " -0.630420 \n", " -0.703226 \n", " -0.677041 \n", " -0.631775 \n", " \n", " \n", " 01-kgpd_Div \n", " 1.564119 \n", " 1.308106 \n", " 1.123155 \n", " 2.333824 \n", " 2.857590 \n", " 2.223117 \n", " \n", " \n", " 02-kgpd_Mul \n", " 2.473648 \n", " 2.027773 \n", " 2.149388 \n", " 3.249448 \n", " 2.624165 \n", " 2.828025 \n", " \n", " \n", " 03-kgpd_Sin \n", " 1.779780 \n", " 0.881090 \n", " 0.280401 \n", " 0.216680 \n", " 0.311288 \n", " 0.427768 \n", " \n", " \n", " 04-kgpd_Div1 \n", " 2.331710 \n", " 1.865534 \n", " 1.411570 \n", " 1.642922 \n", " 4.321977 \n", " 4.466249 \n", " \n", " \n", " 05-kgpd_Pow \n", " 2.097502 \n", " -0.071724 \n", " -0.842765 \n", " -0.932321 \n", " -0.897065 \n", " -0.887837 \n", " \n", " \n", " 06-kgpd_Mul1 \n", " 2.563218 \n", " 2.067909 \n", " 1.842112 \n", " 1.811019 \n", " 4.263897 \n", " 3.320524 \n", " \n", " \n", " 07-kgpd_Exp \n", " 1.756911 \n", " 0.384288 \n", " -0.599693 \n", " -0.759241 \n", " -0.657668 \n", " -0.644029 \n", " \n", " \n", " 08-gpr_MatMul \n", " 0.517953 \n", " 1.502798 \n", " 1.965953 \n", " 4.201281 \n", " 4.281286 \n", " 4.701255 \n", " \n", " \n", " 09-gpr_Add \n", " 1.502111 \n", " 1.461452 \n", " 1.233097 \n", " 1.247736 \n", " 0.486358 \n", " 1.160395 \n", " \n", " \n", "
\n", "
"], "text/plain": ["N 1 10 100 1000 10000 100000\n", "step \n", "00-kgpd_CDist -0.239113 -0.367743 -0.630420 -0.703226 -0.677041 -0.631775\n", "01-kgpd_Div 1.564119 1.308106 1.123155 2.333824 2.857590 2.223117\n", "02-kgpd_Mul 2.473648 2.027773 2.149388 3.249448 2.624165 2.828025\n", "03-kgpd_Sin 1.779780 0.881090 0.280401 0.216680 0.311288 0.427768\n", "04-kgpd_Div1 2.331710 1.865534 1.411570 1.642922 4.321977 4.466249\n", "05-kgpd_Pow 2.097502 -0.071724 -0.842765 -0.932321 -0.897065 -0.887837\n", "06-kgpd_Mul1 2.563218 2.067909 1.842112 1.811019 4.263897 3.320524\n", "07-kgpd_Exp 1.756911 0.384288 -0.599693 -0.759241 -0.657668 -0.644029\n", "08-gpr_MatMul 0.517953 1.502798 1.965953 4.201281 4.281286 4.701255\n", "09-gpr_Add 1.502111 1.461452 1.233097 1.247736 0.486358 1.160395"]}, "execution_count": 33, "metadata": {}, "output_type": "execute_result"}], "source": ["if r is not None:\n", " r = (pivort - pivpy) / pivpy\n", "r"]}, {"cell_type": "markdown", "metadata": {}, "source": ["Based on this, *onnxruntime* is faster for operators *Scan*, *Pow*, *Exp* and slower for all the others."]}, {"cell_type": "markdown", "metadata": {}, "source": ["## Measuring the time with a custom dataset\n", "\n", "We use the example [Comparison of kernel ridge and Gaussian process regression](https://scikit-learn.org/stable/auto_examples/gaussian_process/plot_compare_gpr_krr.html#sphx-glr-auto-examples-gaussian-process-plot-compare-gpr-krr-py)."]}, {"cell_type": "code", "execution_count": 33, "metadata": {}, "outputs": [{"name": "stderr", "output_type": "stream", "text": ["C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\gaussian_process\\kernels.py:409: ConvergenceWarning: The optimal value found for dimension 0 of parameter length_scale is close to the specified lower bound 1e-05. Decreasing the bound and calling fit again may find a better value.\n", " ConvergenceWarning)\n", "C:\\xavierdupre\\__home_\\github_fork\\scikit-learn\\sklearn\\gaussian_process\\kernels.py:418: ConvergenceWarning: The optimal value found for dimension 0 of parameter periodicity is close to the specified upper bound 10.0. Increasing the bound and calling fit again may find a better value.\n", " ConvergenceWarning)\n"]}, {"data": {"text/plain": ["GaussianProcessRegressor(kernel=ExpSineSquared(length_scale=1, periodicity=5))"]}, "execution_count": 34, "metadata": {}, "output_type": "execute_result"}], "source": ["import numpy\n", "import pandas\n", "import matplotlib.pyplot as plt\n", "from sklearn.kernel_ridge import KernelRidge\n", "from sklearn.model_selection import GridSearchCV\n", "from sklearn.gaussian_process import GaussianProcessRegressor\n", "from sklearn.gaussian_process.kernels import WhiteKernel, ExpSineSquared\n", "\n", "rng = numpy.random.RandomState(0)\n", "\n", "# Generate sample data\n", "X = 15 * rng.rand(100, 1)\n", "y = numpy.sin(X).ravel()\n", "y += 3 * (0.5 - rng.rand(X.shape[0])) # add noise\n", "\n", "gp_kernel = ExpSineSquared(1.0, 5.0, periodicity_bounds=(1e-2, 1e1))\n", "gpr = GaussianProcessRegressor(kernel=gp_kernel)\n", "gpr.fit(X, y)"]}, {"cell_type": "code", "execution_count": 34, "metadata": {"scrolled": false}, "outputs": [{"data": {"text/html": ["\n", ""], "text/plain": [""]}, "execution_count": 35, "metadata": {}, "output_type": "execute_result"}], "source": ["onx = to_onnx(gpr, X_test.astype(numpy.float64))\n", "with open(\"gpr_time.onnx\", \"wb\") as f:\n", " f.write(onx.SerializeToString())\n", "%onnxview onx -r 1"]}, {"cell_type": "code", "execution_count": 35, "metadata": {}, "outputs": [], "source": ["from mlprodict.tools import get_ir_version_from_onnx\n", "onx.ir_version = get_ir_version_from_onnx()"]}, {"cell_type": "code", "execution_count": 36, "metadata": {"scrolled": false}, "outputs": [], "source": ["oinfpy = OnnxInference(onx, runtime=\"python\")\n", "oinfort = OnnxInference(onx, runtime=\"onnxruntime2\")"]}, {"cell_type": "markdown", "metadata": {}, "source": ["``runtime==onnxruntime2`` tells the class ``OnnxInference`` to use *onnxruntime* for every node independently, there are as many calls as there are nodes in the graph."]}, {"cell_type": "code", "execution_count": 37, "metadata": {}, "outputs": [], "source": ["respy = oinfpy.run({'X': X_test}, node_time=True)\n", "try:\n", " resort = oinfort.run({'X': X_test}, node_time=True)\n", "except Exception as e:\n", " print(e)\n", " resort = None"]}, {"cell_type": "code", "execution_count": 38, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " i \n", " name \n", " op_type \n", " time_py \n", " time_ort \n", " delta \n", " \n", " \n", " \n", " \n", " 0 \n", " 0 \n", " Sc_Scan \n", " Scan \n", " 0.007998 \n", " 0.005970 \n", " -0.002028 \n", " \n", " \n", " 1 \n", " 1 \n", " kgpd_Transpose \n", " Transpose \n", " 0.000032 \n", " 0.000599 \n", " 0.000567 \n", " \n", " \n", " 2 \n", " 2 \n", " kgpd_Sqrt \n", " Sqrt \n", " 0.000063 \n", " 0.000112 \n", " 0.000049 \n", " \n", " \n", " 3 \n", " 3 \n", " kgpd_Div \n", " Div \n", " 0.000143 \n", " 0.000097 \n", " -0.000045 \n", " \n", " \n", " 4 \n", " 4 \n", " kgpd_Mul \n", " Mul \n", " 0.000038 \n", " 0.000321 \n", " 0.000283 \n", " \n", " \n", " 5 \n", " 5 \n", " kgpd_Sin \n", " Sin \n", " 0.000095 \n", " 0.000146 \n", " 0.000051 \n", " \n", " \n", " 6 \n", " 6 \n", " kgpd_Div1 \n", " Div \n", " 0.000027 \n", " 0.000096 \n", " 0.000069 \n", " \n", " \n", " 7 \n", " 7 \n", " kgpd_Pow \n", " Pow \n", " 0.000299 \n", " 0.000104 \n", " -0.000196 \n", " \n", " \n", " 8 \n", " 8 \n", " kgpd_Mul1 \n", " Mul \n", " 0.000032 \n", " 0.000097 \n", " 0.000065 \n", " \n", " \n", " 9 \n", " 9 \n", " kgpd_Exp \n", " Exp \n", " 0.000383 \n", " 0.000111 \n", " -0.000271 \n", " \n", " \n", " 10 \n", " 10 \n", " gpr_MatMul \n", " MatMul \n", " 0.000080 \n", " 0.004359 \n", " 0.004279 \n", " \n", " \n", " 11 \n", " 11 \n", " gpr_Add \n", " Add \n", " 0.000034 \n", " 0.000165 \n", " 0.000131 \n", " \n", " \n", "
\n", "
"], "text/plain": [" i name op_type time_py time_ort delta\n", "0 0 Sc_Scan Scan 0.007998 0.005970 -0.002028\n", "1 1 kgpd_Transpose Transpose 0.000032 0.000599 0.000567\n", "2 2 kgpd_Sqrt Sqrt 0.000063 0.000112 0.000049\n", "3 3 kgpd_Div Div 0.000143 0.000097 -0.000045\n", "4 4 kgpd_Mul Mul 0.000038 0.000321 0.000283\n", "5 5 kgpd_Sin Sin 0.000095 0.000146 0.000051\n", "6 6 kgpd_Div1 Div 0.000027 0.000096 0.000069\n", "7 7 kgpd_Pow Pow 0.000299 0.000104 -0.000196\n", "8 8 kgpd_Mul1 Mul 0.000032 0.000097 0.000065\n", "9 9 kgpd_Exp Exp 0.000383 0.000111 -0.000271\n", "10 10 gpr_MatMul MatMul 0.000080 0.004359 0.004279\n", "11 11 gpr_Add Add 0.000034 0.000165 0.000131"]}, "execution_count": 39, "metadata": {}, "output_type": "execute_result"}], "source": ["if resort is not None:\n", " df = pandas.DataFrame(respy[1]).merge(pandas.DataFrame(resort[1]), on=[\"i\", \"name\", \"op_type\"],\n", " suffixes=(\"_py\", \"_ort\"))\n", " df['delta'] = df.time_ort - df.time_py\n", "else:\n", " df = None\n", "df"]}, {"cell_type": "markdown", "metadata": {}, "source": ["The following function runs multiple the same inference and aggregates the results node by node."]}, {"cell_type": "code", "execution_count": 39, "metadata": {}, "outputs": [], "source": ["from mlprodict.onnxrt.validate.validate import benchmark_fct\n", "res = benchmark_fct(lambda X: oinfpy.run({'X': X_test}, node_time=True), \n", " X_test, node_time=True)"]}, {"cell_type": "code", "execution_count": 40, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " i \n", " name \n", " op_type \n", " time \n", " N \n", " max_time \n", " min_time \n", " repeat \n", " number \n", " \n", " \n", " \n", " \n", " 24 \n", " 0 \n", " Sc_Scan \n", " Scan \n", " 0.004154 \n", " 100 \n", " 0.004330 \n", " 0.003843 \n", " 10 \n", " 8 \n", " \n", " \n", " 25 \n", " 1 \n", " kgpd_Transpose \n", " Transpose \n", " 0.000013 \n", " 100 \n", " 0.000019 \n", " 0.000010 \n", " 10 \n", " 8 \n", " \n", " \n", " 26 \n", " 2 \n", " kgpd_Sqrt \n", " Sqrt \n", " 0.000018 \n", " 100 \n", " 0.000022 \n", " 0.000015 \n", " 10 \n", " 8 \n", " \n", " \n", " 27 \n", " 3 \n", " kgpd_Div \n", " Div \n", " 0.000025 \n", " 100 \n", " 0.000092 \n", " 0.000015 \n", " 10 \n", " 8 \n", " \n", " \n", " 28 \n", " 4 \n", " kgpd_Mul \n", " Mul \n", " 0.000012 \n", " 100 \n", " 0.000019 \n", " 0.000009 \n", " 10 \n", " 8 \n", " \n", " \n", " 29 \n", " 5 \n", " kgpd_Sin \n", " Sin \n", " 0.000057 \n", " 100 \n", " 0.000070 \n", " 0.000050 \n", " 10 \n", " 8 \n", " \n", " \n", " 30 \n", " 6 \n", " kgpd_Div1 \n", " Div \n", " 0.000014 \n", " 100 \n", " 0.000017 \n", " 0.000011 \n", " 10 \n", " 8 \n", " \n", " \n", " 31 \n", " 7 \n", " kgpd_Pow \n", " Pow \n", " 0.000172 \n", " 100 \n", " 0.000198 \n", " 0.000155 \n", " 10 \n", " 8 \n", " \n", " \n", " 32 \n", " 8 \n", " kgpd_Mul1 \n", " Mul \n", " 0.000020 \n", " 100 \n", " 0.000101 \n", " 0.000009 \n", " 10 \n", " 8 \n", " \n", " \n", " 33 \n", " 9 \n", " kgpd_Exp \n", " Exp \n", " 0.000213 \n", " 100 \n", " 0.000249 \n", " 0.000193 \n", " 10 \n", " 8 \n", " \n", " \n", " 34 \n", " 10 \n", " gpr_MatMul \n", " MatMul \n", " 0.000034 \n", " 100 \n", " 0.000047 \n", " 0.000026 \n", " 10 \n", " 8 \n", " \n", " \n", " 35 \n", " 11 \n", " gpr_Add \n", " Add \n", " 0.000013 \n", " 100 \n", " 0.000019 \n", " 0.000011 \n", " 10 \n", " 8 \n", " \n", " \n", "
\n", "
"], "text/plain": [" i name op_type time N max_time min_time repeat \\\n", "24 0 Sc_Scan Scan 0.004154 100 0.004330 0.003843 10 \n", "25 1 kgpd_Transpose Transpose 0.000013 100 0.000019 0.000010 10 \n", "26 2 kgpd_Sqrt Sqrt 0.000018 100 0.000022 0.000015 10 \n", "27 3 kgpd_Div Div 0.000025 100 0.000092 0.000015 10 \n", "28 4 kgpd_Mul Mul 0.000012 100 0.000019 0.000009 10 \n", "29 5 kgpd_Sin Sin 0.000057 100 0.000070 0.000050 10 \n", "30 6 kgpd_Div1 Div 0.000014 100 0.000017 0.000011 10 \n", "31 7 kgpd_Pow Pow 0.000172 100 0.000198 0.000155 10 \n", "32 8 kgpd_Mul1 Mul 0.000020 100 0.000101 0.000009 10 \n", "33 9 kgpd_Exp Exp 0.000213 100 0.000249 0.000193 10 \n", "34 10 gpr_MatMul MatMul 0.000034 100 0.000047 0.000026 10 \n", "35 11 gpr_Add Add 0.000013 100 0.000019 0.000011 10 \n", "\n", " number \n", "24 8 \n", "25 8 \n", "26 8 \n", "27 8 \n", "28 8 \n", "29 8 \n", "30 8 \n", "31 8 \n", "32 8 \n", "33 8 \n", "34 8 \n", "35 8 "]}, "execution_count": 41, "metadata": {}, "output_type": "execute_result"}], "source": ["df = pandas.DataFrame(res)\n", "df[df.N == 100]"]}, {"cell_type": "code", "execution_count": 41, "metadata": {}, "outputs": [], "source": ["df100 = df[df.N == 100]"]}, {"cell_type": "code", "execution_count": 42, "metadata": {}, "outputs": [], "source": ["%matplotlib inline"]}, {"cell_type": "code", "execution_count": 43, "metadata": {}, "outputs": [{"data": {"image/png": "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\n", "text/plain": [""]}, "metadata": {"needs_background": "light"}, "output_type": "display_data"}], "source": ["fig, ax = plt.subplots(1, 1, figsize=(14, 4))\n", "ax.bar(df100.i, df100.time, align='center', color='orange')\n", "ax.set_xticks(df100.i)\n", "ax.set_yscale('log')\n", "ax.set_xticklabels(df100.op_type)\n", "ax.errorbar(df100.i, df100.time, \n", " numpy.abs(df100[[\"min_time\", \"max_time\"]].T.values - df100.time.values.ravel()),\n", " uplims=True, lolims=True, color='blue')\n", "ax.set_title(\"Time spent in each node for 100 observations\\nGaussianProcess\");"]}, {"cell_type": "code", "execution_count": 44, "metadata": {}, "outputs": [], "source": ["df100c = df100.cumsum()"]}, {"cell_type": "code", "execution_count": 45, "metadata": {}, "outputs": [{"data": {"image/png": "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aXGFOaDqFe7Z9GaaS+zKZOo1ERERkeGgoDNqd7+TKPDJTrsq67UDXyh02Txlpma9/h7wvULqVWoG42aX7k53yrcGJF19BCfdqegGmN1pOvIEM4lM+eX30JmuoCNdSadXkEhX0pmuoNMr6ExXkiK+nS12YqSJkd4yiX9lSwdH1M1nUuiVqa3poKauc9uemnjUC5PpkamJdVIX76DKEtsGMAMdTla9dDvb07tSnmMjIiIiUmzDv5tBALhl7jLuf34tiWQUHCSSaf723Go+/qvHmLxrTRS8JHsGNh3d6RDUbA1yOrtTfQwL61tZzKgqj1NVHqOyLHquKo9TnS6nOpZgl/hmKsP9YTI3tKyKJai2cM+YWGJrekirinWF/ESPm11etfZDXNfyQTq8ijRxkg7V1slnmv44aoeTleocGxEREZFiU1A0FG7awbFUedzw0mVMsThLbQKdHg2xSqbTPLxwDbuWbeoRZFRZgppYF7taFIhUxxJUVXVRVR0FHJnAJBOkVG8JZMLzCY9kBT5xqiviVJXF8l+ZDOCmowa9vf+12y3csv49dJTYcDLNsRERERHZ+RQUjRDvHDOXa5o/tCUgAqi2xNBMxJ/YMLjr2w6lOpxMc2xEREREdr5efvqX4ebz4/9AXby9R9po7znJDCeLkdJwMhEREREZMgqKRohMz0m1dQKUTM/JxZN+ysHVCzWcTERERESGjIKiEaQUe04yw8kmV5T8FdlFREREZIgoKBph1HMiIiIiIjK4dKGFEUYT8UVEREREBpd6ikREREREpKQpKBIRERERkZKmoEhEREREREqagiIRERERESlpCopERERERKSkKSgSEREREZGSpqBIRERERERKmoIiEREREREpaQqKRERERESkpCkoEhERERGRkqagSERERERESpqCIhERERERKWkKikREREREpKQpKBIRERERkZKmoEhEREREREpaQUGRmR1nZi+a2UIz+1qefDOzK0L+PDObPoBlzzMzN7PGrLQLQvkXzew929s4ERERERGR/vQbFJlZHLgSOB44EDjVzA7MKXY8sG94nAX8opBlzWwycCzwalbagcApwOuB44Cfh/WIiIiIiIgMukJ6imYCC919sbt3AbOAk3LKnATc4JFHgbFmtkcBy14GnA94zrpmuXvC3V8BFob1iIiIiIiIDLpCgqKJwLKs98tDWiFl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\n", "text/plain": [""]}, "metadata": {"needs_background": "light"}, "output_type": "display_data"}], "source": ["fig, ax = plt.subplots(1, 1, figsize=(14, 4))\n", "ax.bar(df100.i, df100c.time, align='center', color='orange')\n", "ax.set_xticks(df100.i)\n", "#ax.set_yscale('log')\n", "ax.set_ylim([df100c.min_time.min(), df100c.max_time.max()])\n", "ax.set_xticklabels(df100.op_type)\n", "ax.errorbar(df100.i, df100c.time, \n", " numpy.abs((df100c[[\"min_time\", \"max_time\"]].T.values - df100c.time.values.ravel())),\n", " uplims=True, lolims=True)\n", "ax.set_title(\"Cumulated time spent in each node for 100 observations\\nGaussianProcess\");"]}, {"cell_type": "markdown", "metadata": {}, "source": ["## onnxruntime2 / onnxruntime1\n", "\n", "The runtime ``onnxruntime1`` uses *onnxruntime* for the whole ONNX graph. There is no way to get the computation time for each node except if we create a ONNX graph for each intermediate node."]}, {"cell_type": "code", "execution_count": 46, "metadata": {}, "outputs": [], "source": ["oinfort1 = OnnxInference(onx, runtime='onnxruntime1')"]}, {"cell_type": "code", "execution_count": 47, "metadata": {}, "outputs": [{"data": {"text/plain": ["OrderedDict([('scan0', OnnxInference(...)),\n", " ('scan1', OnnxInference(...)),\n", " ('kgpd_transposed0', OnnxInference(...)),\n", " ('kgpd_Y0', OnnxInference(...)),\n", " ('kgpd_C03', OnnxInference(...)),\n", " ('kgpd_C02', OnnxInference(...)),\n", " ('kgpd_output02', OnnxInference(...)),\n", " ('kgpd_C01', OnnxInference(...)),\n", " ('kgpd_Z0', OnnxInference(...)),\n", " ('kgpd_C0', OnnxInference(...)),\n", " ('kgpd_output01', OnnxInference(...)),\n", " ('gpr_Y0', OnnxInference(...)),\n", " ('GPmean', OnnxInference(...))])"]}, "execution_count": 48, "metadata": {}, "output_type": "execute_result"}], "source": ["split = oinfort1.build_intermediate()\n", "split"]}, {"cell_type": "code", "execution_count": 48, "metadata": {}, "outputs": [{"name": "stdout", "output_type": "stream", "text": ["node scan0\n", "node scan1\n", "node kgpd_transposed0\n", "node kgpd_Y0\n", "node kgpd_C03\n", "node kgpd_C02\n", "node kgpd_output02\n", "node kgpd_C01\n", "node kgpd_Z0\n", "node kgpd_C0\n", "node kgpd_output01\n", "node gpr_Y0\n", "node GPmean\n"]}], "source": ["dfs = []\n", "for k, v in split.items():\n", " print(\"node\", k)\n", " res = benchmark_fct(lambda x: v.run({'X': x}), X_test)\n", " df = pandas.DataFrame(res)\n", " df['name'] = k\n", " dfs.append(df.reset_index(drop=False))"]}, {"cell_type": "code", "execution_count": 49, "metadata": {}, "outputs": [{"data": {"text/html": ["\n", "\n", "
\n", " \n", " \n", " \n", " index \n", " 1 \n", " 10 \n", " 100 \n", " 1000 \n", " 10000 \n", " 100000 \n", " name \n", " \n", " \n", " \n", " \n", " 0 \n", " average \n", " 0.000623 \n", " 0.000592 \n", " 0.000754 \n", " 0.002202 \n", " 0.017529 \n", " 0.201192 \n", " scan0 \n", " \n", " \n", " 1 \n", " deviation \n", " 0.000115 \n", " 0.000030 \n", " 0.000034 \n", " 0.000026 \n", " 0.000976 \n", " 0.000000 \n", " scan0 \n", " \n", " \n", " 2 \n", " min_exec \n", " 0.000541 \n", " 0.000537 \n", " 0.000657 \n", " 0.002169 \n", " 0.016677 \n", " 0.201192 \n", " scan0 \n", " \n", " \n", " 3 \n", " max_exec \n", " 0.000980 \n", " 0.000639 \n", " 0.000780 \n", " 0.002239 \n", " 0.018896 \n", " 0.201192 \n", " scan0 \n", " \n", " \n", " 4 \n", " repeat \n", " 20.000000 \n", " 20.000000 \n", " 10.000000 \n", " 5.000000 \n", " 3.000000 \n", " 1.000000 \n", " scan0 \n", " \n", " \n", "
\n", "
"], "text/plain": [" index 1 10 100 1000 10000 100000 \\\n", "0 average 0.000623 0.000592 0.000754 0.002202 0.017529 0.201192 \n", "1 deviation 0.000115 0.000030 0.000034 0.000026 0.000976 0.000000 \n", "2 min_exec 0.000541 0.000537 0.000657 0.002169 0.016677 0.201192 \n", "3 max_exec 0.000980 0.000639 0.000780 0.002239 0.018896 0.201192 \n", "4 repeat 20.000000 20.000000 10.000000 5.000000 3.000000 1.000000 \n", "\n", " name \n", "0 scan0 \n", "1 scan0 \n", "2 scan0 \n", "3 scan0 \n", "4 scan0 "]}, "execution_count": 50, "metadata": {}, "output_type": "execute_result"}], "source": ["df = pandas.concat(dfs)\n", "df.head()"]}, {"cell_type": "code", "execution_count": 50, "metadata": {}, "outputs": [], "source": ["df100c = df[df['index'] == \"average\"]\n", "df100c_min = df[df['index'] == \"min_exec\"]\n", "df100c_max = df[df['index'] == \"max_exec\"]\n", "ave = df100c.iloc[:, 4]\n", "ave_min = df100c_min.iloc[:, 4]\n", "ave_max = df100c_max.iloc[:, 4]\n", "ave.shape, ave_min.shape, ave_max.shape\n", "index = numpy.arange(ave.shape[0])"]}, {"cell_type": "code", "execution_count": 51, "metadata": {}, "outputs": [{"data": {"image/png": "iVBORw0KGgoAAAANSUhEUgAAAz8AAAE3CAYAAACEmf8HAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjMuMCwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy86wFpkAAAACXBIWXMAAAsTAAALEwEAmpwYAABn1ElEQVR4nO3dd5xcVfnH8c+zvaRX0hMglNAhEERAuoB0lCbSlCKg/pCOSBGpKkhHupEagpjQBAQFAYEk9CSEhBTSe0+2P78/zplkMtkySXZ3tnzfr9e8dufWc+6dO3Of0665OyIiIiIiIi1dVqYTICIiIiIi0hgU/IiIiIiISKug4EdERERERFoFBT8iIiIiItIqKPgREREREZFWQcGPiIiIiIi0Cgp+RKRJM7PrzOyJRtrXfmY2YwOW38fMJjRkmpqypph/M3Mz2zID+z3DzN7dyHW7m9k7ZrbczP5U32nLlE05JplkZg+Y2W8znQ4RaRgKfkSkWmZ2ipmNNrMVZjbbzF41s70zna7amNnjZvb7Btz+OjfW7v5fd9+6ofaXaWY21cwOqml+S89/IzoHWAC0c/eLN3VjZtbDzEaa2az4me2fMj/fzB41s2VmNsfMfp0yf2czG2Nmq+LfnTc1TU1VdQGau5/n7jdkKk0i0rAU/IjIeuLN0J+Bm4DuQF/gPuDoDCZLpKXqB4zzjXjquJnlVDO5CvgncHwNq10HDIz73R+4zMwOjdvLA0YATwAdgb8CI+L0JqeG/IuI1EjBj4isw8zaA78DLnD3v7v7Sncvd/cX3f3SuMw6NSypzcVijcGlZva5ma00s0di055XY9Oef5lZx+rWTVq/2hoHM3sullYvjU2FtovTzwF+TLiRW2FmL8bpPc3seTObb2ZTzOyXSdsqjHlZbGbjgN1rOS7vxH8/i9s/cVPyHZff08zeN7MlZvaZme1Xy/4vN7OZcTsTzOzAOP06MxtuZs/GeR+b2U5J69WW/+vMbJiZDY3rjjWzwXHe3whB74sxv5dVk6bq8n9JzP/SmKaCWvJ0lpmNj8f/NTPrlzTvTjObHmsnxpjZPknzss3sKjP7JqZ7jJn1Sdr0QWY2MW73XjOzGvZfY/7j/G3N7D/x/Iw1s6OS5nW2ULuyzMw+ArZI2fY2ZvaGmS2K5+uEGtLwOHA6az+3B1momfmzhZqbWfH//ORjHj8Pc4DHUrfp7nPd/T5gVA2H/jTgBndf7O7jgYeAM+K8/YAc4M/uXurudwEGHFBD+tvH4zffzKaZ2dVmlrXuInZ3/Dx8lfjcxhlnmNnkeOynmNmPk+bV9tlwM7vAzCYCEy00U/tjSrpGWKzRMrMrkj4r48zs2Dh9W+AB4Dvx2C9JnBNb9/vtbDObFM/lSDPrmZKW86r7vJnZlmb2dsz7AjN7tobzISKNyd310ksvvda8gEOBCiCnlmUeB36f9H4/YEbS+6nAB4Rao17APOBjYBcgH3gLuLa6dZPWPyj+fx3wRNK8s4C2cTt/Bj6tJV1ZwBjgGiAP2ByYDHw/zr8F+C/QCegDfJmalpR0ObBlPeW7F7AQODym8+D4vms1+90amA70jO/7A1skHZ9y4IdALnAJMCX+X1f+rwNKYhqygZuBD6o7DzUcj+ry/xHQMx7T8cB5Nax7DDAJ2JZws3018H7S/FOBznHexcAcoCDOuxT4Ih4XA3YCOiedo5eADoTgbT5waA1pqDH/8fhNAq6Kx+4AYDmwdZz/DDAMKAa2B2YC78Z5xfF8nRnTvyuhWdt2aV5PvyN8jroBXYH3CcFK4phXALcSPlOFtZyfnHg8+idN6xindU+a9kPgi/j/RcCrKdt5Cbi4hn0MJdQUtSV8Lr8GfhrnnRHTelE8nicCS+NnoxhYlnQ8eySOTxqfDQfeiNspBPaNx9uS8riatdfLjwifyayYhpVAj6Q0vlvT+YjnfUE8h/nA3cA7KWmp9vMGPA38Ju63ANi7Pr6j9dJLr017qeZHRFJ1Bha4e8UmbuduDyXQMwkBxofu/om7lwIvEAKCDebuj7r78rid64CdLNRWVWd3QjDxO3cvc/fJhFLuk+L8E4Ab3X2Ru08H7tqYNKVIN9+nAq+4+yvuXuXubwCjCTfiqSoJN16DzCzX3ae6+zdJ88e4+3B3LwduJ9xo7ZlG/iHc+L3i7pXA3wiBxKa4y91nufsi4EVg5xqWOxe42d3Hx8/aTcDOiRJ+d3/C3Re6e4W7/ynmP9G/6GfA1e4+wYPP3H1h0rZvcfcl7v4t8O9a0gA1539PoE3cVpm7v0W4yT3ZzLIJTcqu8VAz+iWheVjCEcBUd38spv9j4HlCkJGOHwO/c/d57j4fuB74SdL8KkIQXeruq9PcZkKb+Hdp0rSlhOAlMX8p60qev0Y8DicCV8Zrcirwp5S0ziPUIpW7+7PABOAHSfnY3swK3X22u4+N02v9bEQ3x+t2NeE6cyBRO/hD4H/uPgvA3Z+Ln8mqmIaJwB61HaQkPwYedfeP4zV8JaGmqH/SMjV93soJTQt7unuJuze7wR9EWiIFPyKSaiHQxTa9Lf3cpP9XV/O+DRsoNne6JTZhWUaoaQDoUsMq/YCesdnSktis5SpCzQyE0uDpSctP29A0VSPdfPcDfpSStr0JJeDrcPdJwP8Rgr15ZvZMctMbkvLg7lXADELe6so/hBqVhFVAwSae+9Tt1XSe+wF3JqVrEaEWpxeAmV0cmz0tjfPbs/Y89wG+WX+TG5yG6pZN5L8nMD0ez4RpMX1dCTUSNX12+gFDUo77j4HNaklHsp4p25sWpyXMd/eSNLeVakX82y5pWjtCrVZifjvWlTw/WRdCrVhqWnslvZ/p7p4yv6e7ryQETucBs83sZTPbJi5T62cjSv7MO6Em7uQ46RTgycR8MzvNzD5N2t721PydkWqdc+HuKwjfkclpqenzdllM90cWmk2eleY+RaQBKfgRkVT/IzQFOqaWZVYCRUnv072pq3NbsTS5aw3LnkIYdOEgws1w/8Rq8W9qh/HpwBR375D0auvuidqV2YQb6YS+G52LDTcd+FtK2ord/ZbqFnb3p9x9b8KNoROaPSWsyUPsb9EbmEXd+a/LBnfA3wDTgXNT0lbo7u9b6N9zOaFmrqO7dyDUPljSultUu9X6Mwvok9J/pS+hedt8QnOumj4704G3U/LWxt1/vgH7Tq7l6BunJWz0eXH3xYTPfXIN305AotZlLLBjot9KtGPS/GQLWFu7kZzWmUnve6Vsa01e3P01dz+YEPB/RaiVhFo+G8lZSUnL08APY+3QEEJNG/H9Q8CFhKaRHQjNW2v6zki1zrkws2JC7fjMGtdIbNh9jruf7e49CbVZ91kGhmEXkXUp+BGRdbj7UkIfkXvN7BgzKzKzXDM7zMxui4t9ChxuZp3MbDNCrcTG+ppQ2v4DM8sltO/Pr2HZtkApoeS1iNAcJtlcQr+WhI+AZRY6hxfGmqPtzSwxsMEw4Eoz62hmvYFf1JHW1O1viieAI83s+zFdBRY6s/dOXdDMtjazAyx0ei8h1CBVJi2ym5kdF2ss/o9wjD6g7vzXpT7zm+oBwrFPDFjR3sx+FOe1JQQX84EcM7uGdWsjHgZuMLOBFuxoZp3rOX0fEgLzy+Lnfz/gSOCZ2ETu78B18foYRBi0IOElYCsz+0lcN9fMdrfQwT4dTwNXm1lXM+tCuB436FlXFgaaSFxH+bbuwBND4/Y7xtqWswn9XAD+Q/hs/dLCwAsXxulvpe4jHodhwI1m1jYGGr9OSWu3uK3ceH63BV6xMBDIUTGYKCXUOCU+07V9Nqrl7p8QPi8PA6+5+5I4q5gQ4MyP2zqTUPOTMBfobTWPZvcUcKaF4b/zCd85H8YmfrUysx8lXc+LYzoqa1lFRBqBgh8RWY+73064ibmacNMwnVBy+o+4yN+AzwjNzl4HNnoUoxhsnU+4aZlJuOGs6UGjQwlNUGYC4wg3+MkeIfSLWWJm/4g3Z0cS2uBPIZRUP0yoNYLQl2JanPd6zFdtrgP+Grdf7ehd6fLQx+hoQjO0xDG+lOq/l/MJgzMsIDSx6RbXSxhBaEK0mNDf4rjYx6Ku/NflZsJN8hIzu2RD8lcXd3+BUHv1jIUmjF8Ch8XZrwGvEgLjaYSAL7mJ2e2Em+7XCZ3mHyF0fK/P9JUBR8U0LSAM9X6au38VF7mQ0LxpDiFweCxp3eXAIYS+VbPiMokBCtLxe0L/r88JAzt8HKdtiNWsbeL2VXyfcC2h2eA04G3gD+7+z5j2MkKt72nAEsIAI8fE6dX5BeGanQy8SwgWHk2a/yFhWO0FwI3AD2P/rCzCQBazCM3avkf4Hqjrs1Gbpwm1wk8lJrj7OEI/pP8RAp0dgPeS1nmLUKs1x8wWpG7Q3d8EfkuoSZpNqHE8KXW5GuwOfGhmK4CRwK/cfUqa64pIA0mMjCIiIs2QmV1HGIHu1EynRUREpKlTzY+IiIiIiLQKCn5ERERERKRVULM3ERERERFpFVTzIyIiIiIirYKCHxGRZsDMXjWz0+teUjaUmV1nZhs0lHRLYGYPmNlvM50OEZHGpOBHRKQaZnaSmX1oZivNbF78//yUBzY2Gnc/zN3/uqnbic8SqjKzFWa23MwmxGefSAtmZmeY2bvJ09z9PHe/oYH292D8bFWZ2RkNsQ8RkY2h4EdEJIWZXQzcCfwB2AzoDpwHfBeo6WGIzcksd29DeHDo5cBD8UGd64gPTZUmwMyyM52GDfQZ4bk9H2c6ISIiyRT8iIgkMbP2wO+A8919uLsv9+ATd/+xu5fG5X5gZp+Y2TIzmx6ft5PYxn5mNiNlu1PN7KD4/x5mNjquO9fMbo/TC8zsCTNbGB8sOsrMusd5/zGzn8X/tzCzt+JyC8zsSTPrkLKvS8zsczNbambPmllBal5jvv5BeDjqoFg78J6Z3WFmi4DrzKy9mQ01s/lmNs3MrjazrKR9nW1m42Mt0jgz2zVO72lmz8f1ppjZL5PW2eD8V3OerjCzb5L2e2zSvDPM7F0z+6OZLY77Pyxp/gAzezuu+wbQpY7PxNlmNsnMFpnZSDPrmTTPzew8M5sY93VvonawtnSYWSczm2FmR8b3beI+TovvHzez+83sFTNbCeyf/BlI3n5daTGzbYEHgO9YqPFbkrSP38f/94vpucxCTedsMzvGzA43s69j3q9K2ldW0jlYaGbDzKxT0mfr3viA0JLajq2ISGNT8CMisq7vAPnAiDqWWwmcBnQAfgD83MyOSXMfdwJ3uns7whPjh8XppwPtgT5AZ0Jt0+pq1jfgZqAnsG1c/rqUZU4ADgUGADsCZ6y3kXADe2zMwxdx8hBgMtANuBG4O6Zpc+B7Mc9nxvV/FPd7GqEW6ShgYQyOXiSU/vcCDgT+z8y+X0/5B/gG2Ccufz3whJn1SJo/BJhACGxuAx5JBCXAU8CYOO+GuN9qmdkBhGN9AtADmAY8k7LYEcDuwE5xue8nzas2He6+CDiLUOvWDbgD+NTdhyatewrhHLQF1mmyVov10uLu4wnH8n/u3sbdO9Sw7mZAAeGcXQM8BJwK7EY41teY2eZx2V8CxxA+Ez0JAfS9aaZRRCRjFPyIiKyrC7DA3SsSE8zs/VgTsdrM9gVw9/+4+xfuXuXunwNPE24E01EObGlmXdx9hbt/kDS9M7Clu1e6+xh3X5a6srtPcvc33L3U3ecDt1ez77vcfVa8yX4R2DlpXs9Y+r8AuBb4ibtPiPNmufvdMf9lwInAlbEGbCrwJ+AncdmfAbe5+6hYizTJ3acRbr67uvvv3L3M3ScTbqRPqo/8x2PwXMxflbs/C0wE9khaZJq7P+TulcBfCYFLdzPrG9P323j83onHpyY/Bh51949jrd+VhBqU/knL3OLuS9z9W+DfKce62nTEPLwOPAe8SQigz03Z9wh3fy/mMd0alNrSUpdy4EZ3LycEeF0IQepydx8LjCUE0sS0/sbdZ8Tjch3wQ1NTSRFp4hT8iIisayHQJfkmzt33iqXlC4nfm2Y2xMz+HZt1LSWUrNfafCrJT4GtgK9i064j4vS/Aa8Bz5jZLDO7zcxyU1c2s25m9oyZzTSzZcAT1ex7TtL/q4A2Se9nuXsHd+/k7ju7e3JNxvSk/7sQ+jhNS5o2jVAzAKGG5ptq8tePGGAlXsBVxJv+Tc1/PAanmdmnSdvfPuUYrMm/u6+K/7Yh1lK4+8qUPNWkZ/J8d19B+Bz0SlqmtmNdUzoSHoxpf8zdF6bsezobrra01GVhDNJgbY3b3KT5q5O21w94Ien4jwcqWXuORUSaJAU/IiLr+h9QChxdx3JPASOBPu7entCnItGsaiVQlFjQQmf1ron37j7R3U8mNC27FRhuZsXuXu7u17v7IGAvQhOm06rZ982AAzvGpmOnJu17UyU/+XoBoTagX9K0vsDM+P90QrO1VNOBKTHASrzauvvhsOn5N7N+hJqkC4HOMTD9kvSOwWygo5kVp+SpJrNIyn9crzNrj8FGi5+LvwBDCc0mt0xZJPUp5Ot8rgjN1NJV3080nw4clnKOC9x9k4+LiEhDUvAjIpLE3ZcQ+pDcZ2Y/jB3Rs8xsZyD5hrktsMjdS8xsD0L/jISvgQILgyLkAlcT+hEBYGanmllXd68ClsTJlWa2v5ntEG+KlxECj0rW1xZYASwxs17ApZue8/XFWoBhwI1m1jYGHb8m1DQBPAxcYma7xY71W8ZlPgKWmdnlZlZoZtlmtr2Z7V5P+S8m3MzPj9s7k1B7kk6epgGjgevNLM/M9gaOrGWVp4AzzWxnM8sHbgI+jE0AN1ViAIGzgD8CQ632Ud0+BY4zs6IYKP10A/Y1F+htZvU1WuEDhM9FPwAz62pmawoM4rEtIASkuRYGs9A9h4hknL6IRERSuPtthJv8y4B5hBvHvxCGhX4/LnY+8DszW07oHD4saf2lcf7DhBqClUDy6G+HAmPNbAWh8/9JsU/HZsBwwo3/eOBt1gYaya4HdgWWAi8Df9/kTNfsF4T0TyZ0un8KeBRCvxtCh/yngOXAP4BOMWg6ktDfZAqhBulhwuAEsIn5d/dxhL5H/yOcmx2A9zYgT6cQBiJYROjzNLSmBeOIZb8FnifUGm3B2r5LG83MdiN8xk6Lx+tWQkB3RS2r3UHohzWX0H/oyQ3Y5VuEPjtzzGzBRiV6XXcSaj5fj9fAB4RjmvA6oZncXoSmfauBfethvyIim8Tc67smXEREREREpOlRzY+IiIiIiLQKCn5ERERERKRVUPAjIiIiIiKtgoIfERERERFpFdIKfszsUDObYGaTzGy9kWjiEKd3xfmfm9mu6axrZr+I88aa2W2bnh0REREREZHq5dS1QHzmwL3AwYShWkeZ2cg41GjCYcDA+BoC3A8MqW1dM9uf8BDBHd291My61ZWWLl26eP/+/TcogyIiIiIi0nqMGTNmgbt3rW5encEPsAcwyd0nA5jZM4SgJTn4ORoY6mHc7A/MrIOZ9QD617Luz4Fb3L0UwN3n1ZWQ/v37M3r06DSSLCIiIiIirZGZTatpXjrN3noB05Pez4jT0lmmtnW3AvYxsw/N7O3Ek79FREREREQaQjo1P1bNtNQno9a0TG3r5gAdgT2B3YFhZra5pzx11czOAc4B6Nu3bxrJFRERERERWV86NT8zgD5J73sDs9JcprZ1ZwB/9+AjoArokrpzd3/Q3Qe7++CuXattuiciIiIiIlKndIKfUcBAMxtgZnnAScDIlGVGAqfFUd/2BJa6++w61v0HcACAmW0F5AELNjVDIiIiIiIi1akz+HH3CuBC4DVgPDDM3cea2Xlmdl5c7BVgMjAJeAg4v7Z14zqPApub2ZfAM8DpqU3eRERERERk0309dzmH3PE2X89dnumkZJQ1p3hj8ODBrtHeRERERETSt6qsgoNvf5tZS0vo2b6QN369L0V56XT9b57MbIy7D65uXloPORURERERkebp0uGfs2BFGe6wYEUplw3/PNNJyhgFPyIiIiIiLdSwUdN5a/w8SiuqACitqOLN8fMYNmp6HWu2TC23vktEREREpDl6qrqnxWycxyb8mfzKrqymPflWxsD8aZRXZTP05a84YeJF9bYfTmkeXWlU8yMiIiIi0gK9t3wnZpZvxpKqdgCUeh5flgzk2/KeHNjuowynLjNU8yMiIiIi0oIsryzkptln8fSiw+iXN4usyiqWVLZbM79t9kp+3m14BlOYOar5ERERERFpIf6zfFcO+fo+nl10COd0eZ5/bvUL7ujzJwqtBIBCK+HW3ndRkFWe4ZRmhmp+RERERESauaUVxdww+2cMX3wwW+Z/y/NbXsouRV8DsH+7MexWPJ73V+zI4OJx7N9uTIZTmzmq+RERERERacb+tWwPDv76Pl5YfADndx3GSwN/tSbwSbi5993sUDiJm3rfk6FUNg2q+RERERERaYYWV7TlulnnMmLJfmxTMIVH+v+OHYq+qXbZPnnzGDHw4kZOYdOj4EdEREREpJl5dele/Hbmz1lS0ZZfdXuKC7oNIy+rItPJavIU/IiIiIiINBMLKtpz7czzeHnpPmxXMImhA65hUOGUTCer2VDwIyIiIiLSxLnDi0v35bqZ57KiqohLug/l3G7Pk2uVmU5as6LgR0RERESkCZtX3pHfzDyfN5Z9h50KJ/CHPneyVcG3mU5Ws6TgR0RERESkCXKHvy85gN/NOpvVVflcudmj/LTrP8ixqkwnrdlS8CMiIiIi0sTMLuvMVTMv5N/Ld2e3onHc1vtOtiiYmelkNXt6zo+IiIhIPfp67nIOueNtvp67PNNJkWbI3Xl20cEc8vV9/G/FDlzT80GGbXGFAp96ouBHREREGl1LDRBWlVVw5mMfMXHeCs58bBSryjT0sKRvxuJVnPboR1w+41cMKpzMa1tdyFldRpKtZm71RsGPiIiINKqWHCBcOvxzFqwowx0WrCjlsuGfZzpJ0gxUVTl/+2Aa37/jHcZMW8wNPe/j6c2vol/+nEwnrcVRnx8RERFpVJcO/5z5y0txh3nLSzh76GguPmRr3J0qDzeCVQ5V7vEV/nd3qqpYMy2xfGViXtJ8d9ZZN8xL3hbrbbuyKmk/nrqfuK+qmudPnr+ST75dQqU7AKUVVbw5fh7DRk3nhN37ZPioS1P17cJVXPb8Z3wweRF7b9mFm4/bgT7/PCzTyWqxFPyIiIhIo3nmo2957cs5VFSFAKG80nlv0kLem/R+hlO2llFFFk6WVWE4WVSRZb5mWtZ688P/C8o7kAXkmFPquWFLFav404i32GvspfTOm7/piTvFN30b0iRUVTmPvz+VP7w2gZws45bjduDE3ftgZplOWoum4EdERERq9lT93YitrsrnpnF/paKqDd1yFtI+azkGrKzKJ8eq+F3vv5BNJVnmKUFHDDLMyaYSSwQiNc0/ejJZWUaWQZYZFv9mmZFthmUl3kPWsOIQ7CRtc2PvPW+fcwoPzT+O1V6wZlqZ5zK3ogt7f/UYuxeN5aiO/+Hw9u/ROWdZ/RxUaZYmz1/BZcM/Z/S0xey/dVduOm4HerQvzHSyWgUFPyIiItLg5pV34Oyp17CsqphcyplX0Zl5dAag0Eo4p+vzfK/tx/Wzs05F6S+bVVY/+wTO7/YcTy86lNUVa4OfrjmLeXLz3/Da0r0YseR7/HbmBVw38zz2afsJR3f4Dwe3+5A22avrLQ3StFVWOY+8O5k/vf41+TlZ/OlHO3Hcrr1U29OIFPyIiIhIg/q6pC9nTrmWRRXtua/vzVw76zzmV3RaM79t9kp+3m14BlNYPwqyyrmt952cP+1KVnsBhVbCrb3vYmDBDAYWDOOCbsP4qqQ/I5Z8jxeXfI+Lpl9CgZVwYLuPOLrD23yv7Rjys1rO4A+yrolzl3PJ8M/5bPoSDh7UnRuP2Z5u7QrqXlHqlYIfERERaTDvLt+Jn0+7koKsMoZtcTk7FH1DYVbpegFCQVZ5ppNaL/ZvN4bdisfz/oodGVw8jv3bjVkzzwy2LZzKtoVTuWyzoXy8ahtGLPkeLy/Zh5eX7ku77BUc1u49ju74NkOKv9Twxi1EeWUVD74zmTv/NZHi/GzuOnkXjtyxh2p7MkTBj4iIiDSIYYsO5qoZF7BFwQwe7X89vWKH/9oChJbg5t53c+G0y7mp9z01LpNlzuDi8QwuHs81PR/ivRU7MXLxfry0dB+eXfx9uuUs5IgO/+XoDm+zY+HEje6HJJk1fvYyLh3+GV/OXMYPdujB9UdvR5c2+ZlOVqum4EdERETqVZUbf5zzE+6bfwL7tPmY+/rdTNuUfi3pBAjNVZ+8eYwYeHHay+daJfu1/Zj92n7M6qp83lo2mBFL9uOJhT/g0QXH0D9vFkd1eJujOrzNlg2Ybqk/ZRVV3PvvSdz770l0KMrl/h/vymE79Mh0sgQw9+YzZOLgwYN99OjRmU6GiIhI67GBo72VVOVyyfSLeGnpvpzc6Z/8rtf95FplAyWuBhsyHHQ9jmZX35ZWFq8ZKOH9FTviZLFdz3YctVNPjtypJz07aHSwpujLmUu55LnP+GrOco7ZuSfXHrkdHYvzNmwjTfhzWaMmNAy7mY1x98HVzUur5sfMDgXuBLKBh939lpT5FucfDqwCznD3j2tb18yuA84GEoPeX+Xur2xY1kRERKSpWFTRjrOnXs2YVYO4YrPHOLfr82qutQnaZ6/khE5vcEKnN5hX3pGXlu7DiOzLuPnVr7j51a/YY0AnjtqpJ4fv0INOG3pzLfWutKKSu96cyANvT6ZzcR4PnTaYgwd1z3SyJEWdwY+ZZQP3AgcDM4BRZjbS3cclLXYYMDC+hgD3A0PSWPcOd/9jveVGREREMmJyaU/OnHIds8u7cG/fm/lBh/cynaQWpVvuYs7qMpKzThnB1AUrefGzWfzj05lc/Y8vuW7kWPbdqitH79yTg7btTnG+ejU0tk++Xcylwz9n0rwV/HC33vz2B4NoX5Sb6WRJNdK5OvYAJrn7ZAAzewY4GkgOfo4GhnpoQ/eBmXUwsx5A/zTWFRERkWbswxXbcc60q8mhkqc3v4rdir/KdJJatP5divnFgQO58IAtGTd7GSM/m8WLn87ira/mUZibzUGDunP0Tj3Zd6uu5OVkZTq5LVpJeSW3v/E1D/93Mt3bFfD4mbuz39bdMp0sqUU6wU8vYHrS+xmE2p26lumVxroXmtlpwGjgYndfnLpzMzsHOAegb9++aSRXREREGss/Fu/HZTN+RZ+8OTzW/zr65s/NdJJaDTNju57t2a5ney7//jaMnraYEZ/O5JUvZvPiZ7NoX5jL4TtsxlE79WKPAZ3IzlIbxPo0euoiLhv+OZMXrOTkPfpy1eHb0LZAtT1NXTrBT3VXSmqPppqWqW3d+4Eb4vsbgD8BZ623sPuDwIMQBjxII70iIiLSwNzhrnknccfcU9mz+HP+0u9G2ueszHSyWq2sLGOPAZ3YY0AnrjtqO96duIARn85kxKezePqj6XRvl8+RO/bk6J17sX2vdnrGzCZYVVbBH16bwOPvT6VXh0Ke/NkQvrtll0wnS9KUTvAzA+iT9L43MCvNZfJqWtfd1xQNmdlDwEtpp1pEREQypqwqhytnXsjziw/iuI5vckuvu8nLqsh0siTKzc5i/226sf823VhdVsm/xs9lxKez+Ov/pvLwu1PYvEsxR+7Uk6N27skWXdtkOrnNyv++Wcjlz3/Ot4tWcfp3+nHZoduoj1Uzk87ZGgUMNLMBwEzgJOCUlGVGEpqwPUNo1rbU3Web2fya1jWzHu4+O65/LPDlJudGREREGtTSimLOnfYbPli5Ixd1f4JfdntGI7o1YYV52RwZh8ZeuqqcV7+czYhPZ3HXWxO5882J7NCr/ZqhszdrX5Dp5DZZK0oruOXV8Tzxwbf061zEs+fsyZDNO2c6WbIR6gx+3L3CzC4EXiMMV/2ou481s/Pi/AeAVwjDXE8iDHV9Zm3rxk3fZmY7E5q9TQXOrcd8iYiISD37trQ7Z0y9jhllm3FHnz9ybMf/ZDpJsgHaF+Vy0h59OWmPvsxZWsJLn89i5GezuPGV8dz06niGDOjEUTv14vAdNqNDkYbOTvjvxPlc8fwXzFq6mp/uPYBLDtmawrzsTCdLNpIecioiIiI1iw9b/Hjl1pw99bdUksVf+t3IkDZj61gxg1rIQ06r1QAPkpyyYCUjP53FiM9mMnn+SnKzje9t1ZUjd+rJwYO6U5S3tqz867nLufCpj7nnlF3Zqnvbek9LpiXnb7P2Bdz08nieGTWdLboWc9sPd2K3fh0bJyHN7XMJzeYhpwp+REREpGZPGS8v+S6/nv5rNstdyGMDrmPz/NSuv02Mgp+N4u6MnRWGzh756SzmLCuhMDebQ7brztE792S3fh05/M7/MmtpCT3bF/LGr/ddJzBq7laVVXDw7W8za2kJnYryyMk25i8v5Zx9t+D/DhpIQW4j1vY0t88lNJvgp+V8YkVERKReuTt/mXc8t8w5k92KxvFQ/9/TKWdZppMlDcTM2L5Xe7bv1Z4rDt2GUVMXMeKzWbzyRegnlJttVFY57jBveQnnDB3NZYdugyUN7ltd/6/kadUtW9f8ML267de1rFWzZPX7M4NrRn7JvOWluMPClWW0zc/hhfO/y059OqyfKWm2FPyIiIjIesorq7hmxFiennMmR7R/hz/2uYOCrPJMJ0saSVaWMWTzzgzZvDPXHbkdN70ynr/9bxpVsXC/vNJ5d9JC3r3nvcwmtAGVV1YxYc5yBT8tjIIfERERWceyknIuePJj/jtxARd0e5aLuz9BljWdJi2SpnpqOpUHjP76DrbMzaZt9iqWVxXjGCsrC8i2Kq7p9TAQnv0E4En1LDX9X+18N9jnuXW2FZbxaqYB75283nSq2V/y7JrSc/ucU6isyqIou5TirNUUZZWypKKYoS9P4ISJF62X7o3ShJqFtWYKfkRERGSNmUtWc9Zjo/hm/gpuO35HTph4RKaTJE3AAe1G8dD841hdtnY47EIr4Zyuz3NQu4/qb0c79Eh/2bHv1Ntup5VuxkPzj2NO5fr5k5YlK9MJEBERkabhixlLOebe95i1ZDWPn7kHJ+zep+6VpFU4v9tztMletc60ttkr+Xm34RlKUf1q6fmTtRT8iIiICG+Mm8sJf/kfedlZPH/+Xuw9sEumkyRNSEFWObf1vpNCKwFCrcitve9qMf3AWnr+ZC0FPyIiIq3cY+9N4Zy/jWar7m144YK9WuTzW2TT7d9uDLsVjyeLSgYXj2P/dmMynaR61dLzJ4GCHxERkVaqssq5buRYrn9xHIcM6s4z53yHbm0L6l5RWq2be9/NDoWTuKn3PZlOSoNo6fkTDXggIiLSKq0sreCXT3/Cm1/N4+x9BnDFYduSndUMH6wojapP3jxGDLw408loMC09f6LgR0REpNWZu6yEsx4fxfjZy7jhmO35yZ79Mp0kEZFGoeBHRESkFRk/exlnPT6KZavLeeT03dl/m26ZTpKISKNR8CMiItJK/GfCPC586hPa5Ocw7LzvsF3P9plOkohIo1LwIyIi0go8+eE0rhkxlq27t+XRM3Zns/Ya2EBEWh8FPyIiIi1YVZVzyz+/4sF3JrP/1l25+5RdaZOvn38RaZ001LWIiDRbX89dziF3vM3Xc5dnOilNUkl5JRc89TEPvjOZ077Tj4dOG6zAR0RaNQU/IiLSLK0qq+DMxz5i4rwVnPnYKFaVVWQ6SU3K/OWlnPTgB/xz7Byu/sG2XH/UduRk62dfRFo3fQuKiEizdOnwz1mwogx3WLCilMuGf57pJDUZE+cu59j73uOrOct44NTd+Nk+m2OmZ/iIiCj4ERGRZmfYqOm8OW4upRVVAJRWVPHm+HkMGzU9wynLvPcnLeC4+9+npLyKYed+h+9vt1mmkyQi0mSo4a+IiDS8p+q31uHRCXdCZS9g7YhlFeUl3PjCu6z+31PsUvQV2xRMJS9rE5rCneKbntBG9tzo6Vz59y/YvGsxj56xO707FmU6SSIiTYqCHxERaVamlvZgdkU3Sjx/nemVZFFBDtfOOg+APCtjh8JJ7FI0gV2KvmLnoq/pmTufltj6y925/Y2vufutSey9ZRfuO3VX2hXkZjpZIiJNjoIfERFpNj5ZtRU/nXIthtMhezlLKtutmdclZwlvb/0zFle255NVW/PJqm34dNVWDF34Ax5ecCwA3XIWxmAoBEQ7FE2iKKs0U9mpF6UVlVw2/HNGfDqLEwf34ffHbk+uBjYQEamWgh8REWkWXl86hF9+eyndchfz+IBrmVbag/OnXclqL6DQSri1910UZpdTmL2AnnkL+EGH9wAoq8rhq5L+fLJqGz5ZtTWfrtqa15btBUA2lWxdMHVNMLRL0QQG5M8iy5pHk7dFK8s492+jGTV1MZcdujU//94WGthARKQWCn5ERKTJ++uCI7hu1jnsWDiRRwb8ji45S9k8fxa7FY/n/RU7Mrh4HPu3G1PtunlZFexYNIkdiyZxOi8BsLCiHZ+t2mpNQDRyyfd4ctHhALTLXsHOhRPY5Y2v2aVvB3bu04EORXmNltd0TVmwkjMf+4hZS0u455RdOGLHnplOkohIk6fgR0REmqwqN26ZfQYPLjieg9p9wN19/0BhUjO1m3vfzYXTLuem3vds0HY75yzjgHajOaDd6DX7+aa095pg6JNVW3P3WxOpihVAm3cpZue+Hdilb0d26dOBbTZrm9Fn5oyauoizh44my4ynzx7Cbv06ZSwtIiLNiYIfERFpkkqqcrlk+kW8tHRfTuv8Etf2fJBsq1pnmT558xgx8OJN3leWOQMLpjOwYDondHoDgBXHl/P5jCV88m14vfP1fP7+8UwACnKz2LFXB3bpm3h1pHu7gtp2UW9GfDqTS5/7nN4dC3nszN3p17m4UfYrItISKPgREZEmZ0lFG86ZdjUfrdyeKzd7lHO6/r3RR2lrk5/DXlt0Ya8tugBhRLUZi1fzyfQlfPLtYj75dgmPvTeVv7wTArIe7QtCINSnI7v07cD2vdpTkJtdb+lxd+799yT++PrX7DGgEw/+ZLcm2RxPRKQpSyv4MbNDgTuBbOBhd78lZb7F+YcDq4Az3P3jNNe9BPgD0NXdF2xadkREpLmbXtaNM6Zcz/Syzbir720c1eGdTCcJADOjT6ci+nQq4qidQv+a0opKxs1aFmqHYlD0yhdzAMjJMrbt0W5t7VCfjvTrXJT2gARfz13OhU99zD2n7Er/zsVc9cIXDB8zg+N26cXNx+9Afk79BVYiIq1FncGPmWUD9wIHAzOAUWY20t3HJS12GDAwvoYA9wND6lrXzPrEed/WX5ZERKS5+mLVFpw59TrKPJe/DbiaIW3GZjpJtcrPyQ79gPp2XDNt/vJSPk2qHRo+ZgZD/zcNgI5FuezcJ/Yd6tuBnfp0qPZ5PKvKKtYMZnD6Ix/Rt3MRH05ZxP8dNJBfHThQI7qJiGykdGp+9gAmuftkADN7BjgaSA5+jgaGursDH5hZBzPrAfSvY907gMuAEfWQFxERacb+vWwwF3x7OR2zl/HM5leyZcGMTCdpo3Rtm8/Bg7pz8KDuAFRWORPnLY99h0JA9O8J8wEwgy27tlknINqqe1suHf45C1aU4Q5zlpUwZ3kJt5+wE8ft2juTWRMRafbSCX56AdOT3s8g1O7UtUyv2tY1s6OAme7+WW0lWGZ2DnAOQN++fdNIroiINDdPL/w+V888n20Lp/Bo/+vplrs400mqN9lZxjabtWObzdpx8h7hd2xZSTmfT18agqHpS/jX+Lk8NyYEe3nZWVRUVa0Zac6BvKwsKiqbx7OHRESasnSCn+oik9Rv4JqWqXa6mRUBvwEOqWvn7v4g8CDA4MGD9c0vItKCuMOf5p7KPfNOYr+2o7m37y0UZ5dkOlkb7qkNa4bWDtg7vsgD3wKmlfXg01Vb87tZP2MVBZSST56VsXX+NEqrchj68gROmHhR/aT3FP2cikjrlE7wMwPok/S+NzArzWXyapi+BTAASNT69AY+NrM93H3OhmRARESap7KqHC6f8UteWHIAJ3V6jd/3upeclKGsWwsz6J8/m/75s5lc2pOH5h+HY5R6Pp+XbEWhlXBO1+cznUwRkWYvnSe0jQIGmtkAM8sDTgJGpiwzEjjNgj2Bpe4+u6Z13f0Ld+/m7v3dvT8heNpVgY+ISOuwrLKIM6ZezwtLDuCS7kO5udfdrTbwSXV+t+dok71qnWlts1fy827DM5QiEZGWo87gx90rgAuB14DxwDB3H2tm55nZeXGxV4DJwCTgIeD82tat91yIiEizMausCz/65jY+WrEdt/f5Exd2H9boz/Bpygqyyrmt950UWmj+V2gl3Nr7LgqyyjOcMhGR5i+t5/y4+yuEACd52gNJ/ztwQbrrVrNM/3TSISIizdu41QM4c8p1rKoq4K8DruW7bT/LdJKapP3bjWG34vG8v2JHBhePY/92YzKdJBGRFiGdZm8iIiKb7L/Ld+aEb27FzHlui8sU+NTh5t53s0PhJG7qfU+mkyIi0mKkVfMjIiKyKZ5bdCBXzvgFWxZM57H+19Ejb2Gmk9Tk9cmbx4iBF2c6GSIiLYqCHxERaTDuzl1vTuKOGRexd5tPuK/fzbRL6cwvIiLSWBT8iIhIgyivrOI3L3zBsNEzOL7jv7i51z3kZVVkOlkiItKKKfgREZF6t6K0gvOf/Jh3vp7PLw8cyEXzjtCIbiIiknEKfkREpF7NXVbCmY+NYsLc5dx6/A6cuHtfeCrTqRIREVHwIyIi9ejrucs549GPWLq6nEdOH8x+W3fLdJJERETWUPAjIiL14v1vFnDu38ZQkJvNs+d+h+17tc90kkRERNah4EdERDbZiE9ncslzn9GvczGPn7k7vTsWZTpJIiIi61HwIyIiG83duf/tb7jtnxMYMqATD/5kMO2LcjOdLBERkWop+BERkY1SUVnFtSPH8uSH33LUTj35w492JD8nO9PJEhERqZGCHxER2WCryir4xVOf8OZX8zjve1tw2fe3JitLY1mLiEjTpuBHREQ2yPzlpfz0r6P4cuZSbjhme36yZ79MJ0lERCQtCn5ERCRt38xfwRmPfcSC5WU8+JPBHDSoe6aTJCIikjYFPyIikpbRUxfxs6GjyckynjlnT3bq0yHTSRIREdkgCn5ERKROr3wxm/979lN6dyjk8TP3oG9nDWUtIiLNj4IfERGpkbvzyLtTuPGV8ezatyMPnzaYjsV5mU6WiIjIRlHwIyIi1aqscm54aRyPvz+Vw7bfjDtO3JmCXA1lLSIizZeCHxERWU9JeSW/euYTXhs7l5/uPYDfHL6thrIWEZFmT8GPiIisY9HKMn7611F8On0J1xwxiLP2HpDpJImIiNQLBT8iIrLG1AUrOeOxj5i9tIT7TtmVw3bokekkiYiI1BsFPyIiAsAn3y7mp38djbvz1NlD2K1fp0wnSUREpF4p+BEREV4fO4dfPvMJ3doW8PiZu7N51zaZTpKIiEi9U/AjItLKDf3fVK4dOZYde3fgkdMH06VNfqaTJCIi0iAU/IiItFJVVc6t//yKv7wzmYO27c7dJ+9CYZ6GshYRkZZLwY+ISCtUUl7JJc99xkufz+a07/Tj2iO3I1tDWYuISAuXlc5CZnaomU0ws0lmdkU1883M7orzPzezXeta18xuiMt+amavm1nP+smSiIjUZsmqMk579CNe+nw2Vx62DdcfpcBHRERahzqDHzPLBu4FDgMGASeb2aCUxQ4DBsbXOcD9aaz7B3ff0d13Bl4Crtnk3IiISK2mL1rF8fe/z6ffLuGuk3fh3O9tgZkCHxERaR3SqfnZA5jk7pPdvQx4Bjg6ZZmjgaEefAB0MLMeta3r7suS1i8GfBPzIiIiKb6eu5xD7nibr+cu54sZSzn2vveZv7yUv/10D47aSRXuIiLSuqTT56cXMD3p/QxgSBrL9KprXTO7ETgNWArsn3aqRUSkTqvKKjjzsY+YtbSEkx/8gFXllXQqyuOZc4awZbe2mU6eiIhIo0un5qe69hCptTQ1LVPruu7+G3fvAzwJXFjtzs3OMbPRZjZ6/vz5aSRXREQALh3+OQtWlOEOC1eWkZdtvHD+Xgp8RESk1Uon+JkB9El63xuYleYy6awL8BRwfHU7d/cH3X2wuw/u2rVrGskVEWm93J25y0q4fuRYXvtyDqUVVWvmlZZX8Z8JKkQSEZHWK51mb6OAgWY2AJgJnASckrLMSOBCM3uG0KxtqbvPNrP5Na1rZgPdfWJc/yjgq03OjYhIc/bUhg08UOXG1LIejF29BeNWb87Y1ZszrmRzFlR0XLNMvpXSKXsZfXLnsLSymKEvT+CEiRfVT3pPUVdNERFpXuoMfty9wswuBF4DsoFH3X2smZ0X5z8AvAIcDkwCVgFn1rZu3PQtZrY1UAVMA86r15yJiLQgpVU5TCzpx9iSzWOwM4DxJQNYWVUEQK6VMzD/W/ZvO5pBhZP5ctXmvLxkH0q8gNkVXZld0ZVCK+Gcrs9nOCciIiKZk9ZDTt39FUKAkzztgaT/Hbgg3XXj9GqbuYmItHbLKosYv3oAY0u2CLU5qzdnYklfKuJXdnHWKgYVTOFHHf/FoMLJDCqczFb535KXVbFmGyVVubyzYjdKKgrWTGubvZKfdxve6PkRERFpKtIKfkREpP65O/OWlzJu1jLGzlrK2GlXMnb15nxb1mPNMl1yFrNd4Tfs33Y02xV+w3aFk+mbN4csq73JWUFWObf1vpPzp13Jai+g0Eq4tfddFGSVN3S2REREmiwFPyIijaCqypm6cCVjZy1j3Oxl4e+spSxYUbZmmX55A9i+8BtO7PQ6gwoms13hN3TLXbLR+9y/3Rh2Kx7P+yt2ZHDxOPZvN6YeciIiItJ8KfgREalnpRWVTJy7ItTmzFrGuFnLGD97GSvLKgHIzTYGdmvLflt3Y7ue7diuZ3u27dGWtn/Pq/e03Nz7bi6cdjk39b6n3rctIiLS3Cj4ERHZBMtKyhk/K9TkJGp1Js5dTkVVaJZWnJfNoJ7t+NHgPgzq0Y5BPdsxsHsb8nOyGyV9ffLmMWLgxY2yLxERkaZOwY+ItHpfz13OhU99zD2n7MpW3at/AOh6/XNisPPtolVrlunSJp/terZj/627sl3P9gzq2Y5+nYrIytqwIaxFRESkYSj4EZFWbVVZBWc+9hGzlpZw5mOjeOPX+1KQk113/5zORWzfqx0n7t6HQT3bsV3PdnRrW1DLnkRERCTTFPyISJ3SqRlpLtyd0ooqVpdVsrq8kiv//gXzlpfiDrOXrua7t7xFWUXVmv45OVnGwO7V9M8pyM1wTkRERGRDKfgRkVpVVzNSlNcwXx3uTkl5FavLQ2CyuqySkvJKVpWt+351nFYSpyUvv977lPVWl1fiNYwSXeWwdHU5e27emWN27tXo/XNERESkYSn4EZFaXTr8cxasKMMd5i8v4f+e+ZRrjhwUA4+qGIhUrA0u4rTVZRXrvC+Jy60ur6KkhgBldXnlBqcvi0qKskopyCqlMKuUQiulMKuEwqxSusRpBVmlFBWUUFiY9D6rhAfnHYs7tM1eTWFWKflWxtLKYpbNnMgJxRfBxHo4gKfU/jweERERaTwKfkTqSVNrGuburC6vZEVpBStLK1lZWhH/r6h22sqyClakTJuztISFK9f2cymrdF4fN5fXx81NKw1ZBkV5ORTkZlOUl01hbjYFedkU5mbRtW1+eJ+bTWFeFoW52RTm5YS/uVkU5iW/D8sU/GswRWuCnBIKskrJswpsI8cTWFTRjofmH8fsyu5rphVaCed0fX7jNigiIiJNmoIfkXpQX03DSisq0wpUVpTFgKW0cm3wkpi/ZBorKwtZWVVAFek11yq0EoqzV9MmazXFWasozl5N96zVzFi9Le2znMKsUrKpIsuqKK3KJdcqubznXym0UMOy/quEQislN53A5IQNqBkpnJL+smk4v9tzPL3oUFZXrB2ooG32Sn7ebXi97kdERESaBgU/IvXg18M+W9Npft6yEn7yyEecskffWJuyfqCy3rQYzJRXphcI5GVnUZyfTXF+Dm3ycyjOz6F9UR69OhZSXPEJxVmraZO9KvzNWk1x9up1/m+TFeaF6SVkW1W1+7l9zik8NP84lla0WzMtUTNyVId36uXYZVJBVjm39b6T86ddyWovoNBKuLX3XRRklWc6aSIiItIAFPyIpKmyypm1ZDVTFqxc85q8YCVfzlzKoqSmYeVVzphpixkzbfGaaVnGOoFK+D+bLm3y15u29v+UaXlrp+XlZNWc0KcG11ueW0PNyP7txrBb8XjeX7Ejg4vHsX+7MZlOkoiIiDQQBT/S+jxVczssd1hQ0YEpZb2YUtozvnoxpbQXU8t6UOZ5a5YtzlrFgPxZVJZ2p3NWBe1zVpBrlWRRyarKfPKyKnhqi6tpk72aAiutuflXJbAqvmqSoU7zraVm5Obed3PhtMu5qfc9mU6KiIiINCAFP9IqLa8sZGppTyaX9oqBTq81gc7yquI1y+VaOf3yZtM/fxb7tR3NgPxZDMifyeb5M+masxiztU3DFpZ1XLNeoZVwTqfn6Zq7JAO5q1+toWakT948Rgy8ONPJEBERkQam4EdarNKKSr5duIrJiWZq82NTtRl/Y0HF2kDFqKJn7nw2z5/JsR3/zYD8mSHAyZtJz7z55NTQHyahNTQNU82IiIiItAQKfqRZS/TDmbxgJVPmrwhBzsJVTFmwgpmLV1OV1FqsS5s8BnQp5oC2o2KAM4vN82fSN2/2JjXjag1Nw1QzIiIiIi2Bgh9pNBv7HBx3Z/6KUqbMX8nUhStjoBNqcaYtXEVZ5dqamTb5OQzoUswufTpy3C692bxrMf07F9O/SzHtC3PDQk99t76z1iqahomIiIg0dwp+pFGk8xycZSXlTE2MojZ/5Tqjqq0orVizXF52Fv06F4VanG27sXmXEOAM6FpM1zb52MY+8XITqWmYiIiISNOm4KeJ2djakabu0uGfs2BFWXgOzvLwHJyDtu3OlAUr1gQ4C1asHS7aDHp3LGRAlzbs2rcDA7oUM6BrGzbvUkzPDoVkZ2UmwKmNmoaJiIiING0KfpqQdGpHGlNVlbO6vJKVZRWsLqtkZWklq8oqWFlWyarS+LesYu30+HdVyvTZS0uYv7yURPeb8sq1z8Hp2jafAV2KOXCb7gzoWsyALsVs3qWYPp2KKMjNzljeRURERKTlUfDThCTXjixYUcplwz/nnlN2TWvdsoqqNYHJ6hh4rCyrYFXib1klK0vj36Tpq8sqqw9mVi1hVVVh2mk3qijOKqEoa/Xav9kldMwqYcrKrWmbBYVZpeRYJQVWSkVVFkXZpbw64FcxA8DM+NoYGXoOjoiIiIg0Hwp+mohho6bz5ri5lFaEzvulFVX888s5nPrwh/TuWLhOUFNd7Ut5Zfo3//k5WRTlZVOUl0Nx/tq/HYvzKM7Lpig/h+JvnqYoqyS8shMBTQnFWavX/C3OXhvs5FtZjQ/xTDwHZ1nF2mZ8iefgiIiIiIg0FgU/G+up+u1zMvTrO+hleXxDvzXTKqqqeH/SXLrmLKE4azWFWSVralN6J4KQotUUtSmhODsRlJSE5ZKClKK4XtGJsynKzSYnOyuN/D1ab3lrDc/BEREREZGmT8FPE3FAu1E8OO+4daYVUMq53Z7nos2erp+dFOTWz3Y2dLet4Dk4IiIiItL0pVEFII3h/G7P0TZn1TrT2uW0nNqRxHNwsqjUc3BEREREJCMU/DQRidqRQisBaJG1Izf3vpsdCifpOTgiIiIikhFpBT9mdqiZTTCzSWZ2RTXzzczuivM/N7Nd61rXzP5gZl/F5V8wsw71kqNmrKXXjiSeg9Mnb16mkyIiIiIirVCdwY+ZZQP3AocBg4CTzWxQymKHAQPj6xzg/jTWfQPY3t13BL4Grtzk3LQAqh0REREREWkY6dT87AFMcvfJ7l4GPAMcnbLM0cBQDz4AOphZj9rWdffX3b0irv8B0Lse8tPsqXZERERERKRhpBP89AKmJ72fEaels0w66wKcBbyaRlpEREREREQ2SjrBT3UPtEl9omZNy9S5rpn9BqgAnqx252bnmNloMxs9f/78NJIrIiIiIiKyvnSCnxlAn6T3vYFZaS5T67pmdjpwBPBjd08NqABw9wfdfbC7D+7atWsayRUREREREVlfOsHPKGCgmQ0wszzgJGBkyjIjgdPiqG97AkvdfXZt65rZocDlwFHuvgoREREREZEGlFPXAu5eYWYXAq8B2cCj7j7WzM6L8x8AXgEOByYBq4Aza1s3bvoeIB94w8wAPnD38+ozcyIiIiIiIgl1Bj8A7v4KIcBJnvZA0v8OXJDuunH6lhuUUhERERERkU2Q1kNORUREREREmjsFPyIiIiIi0ioo+BERERERkVZBwY+IiIiIiLQKCn5ERERERKRVUPAjIiIiIiKtgoIfERERERFpFRT8iIiIiIhIq6DgR0REREREWgUFPyIiIiIi0ioo+BERERERkVZBwY+IiIiIiLQKCn5ERERERKRVUPAjIiIiIiKtgoIfERERERFpFRT8iIiIiIhIq6DgR0REREREWgUFPyIiIiIi0ioo+BERERERkVZBwY+IiIiIiLQKCn5ERERERKRVUPAjIiIiIiKtgoIfERERERFpFRT8iIiIiIhIq6DgR0REREREWgUFPyIiIiIi0ioo+BERERERkVYhreDHzA41swlmNsnMrqhmvpnZXXH+52a2a13rmtmPzGysmVWZ2eD6yY6IiIiIiEj16gx+zCwbuBc4DBgEnGxmg1IWOwwYGF/nAPense6XwHHAO5ueDRERERERkdqlU/OzBzDJ3Se7exnwDHB0yjJHA0M9+ADoYGY9alvX3ce7+4R6y4mIiIiIiEgt0gl+egHTk97PiNPSWSaddWtlZueY2WgzGz1//vwNWVVERERERGSNdIIfq2aap7lMOuvWyt0fdPfB7j64a9euG7KqiIiIiIjIGjlpLDMD6JP0vjcwK81l8tJYV0REREREpMGlU/MzChhoZgPMLA84CRiZssxI4LQ46tuewFJ3n53muiIiIiIiIg2uzpofd68wswuB14Bs4FF3H2tm58X5DwCvAIcDk4BVwJm1rQtgZscCdwNdgZfN7FN3/359Z1BERERERATSa/aGu79CCHCSpz2Q9L8DF6S7bpz+AvDChiRWRERERERkY6X1kFMREREREZHmTsGPiIiIiIi0Cgp+RERERESkVVDwIyIiIiIirYKCHxERERERaRUU/IiIiIiISKug4EdERERERFoFBT8iIiIiItIqKPgREREREZFWQcGPiIiIiIi0Cgp+RERERESkVVDwIyIiIiIirYKCHxERERERaRUU/IiIiIiISKug4EdERERERFoFBT8iIiIiItIqKPgREREREZFWQcGPiIiIiIi0Cgp+RERERESkVVDwIyIiIiIirYKCHxERERERaRUU/IiIiIiISKug4EdERERERFoFBT8iIiIiItIqKPgREREREZFWQcGPiIiIiIi0Cgp+RERERESkVUgr+DGzQ81sgplNMrMrqplvZnZXnP+5me1a17pm1snM3jCzifFvx/rJkoiIiIiIyPrqDH7MLBu4FzgMGAScbGaDUhY7DBgYX+cA96ex7hXAm+4+EHgzvhcREREREWkQ6dT87AFMcvfJ7l4GPAMcnbLM0cBQDz4AOphZjzrWPRr4a/z/r8Axm5YVERERERGRmpm7176A2Q+BQ939Z/H9T4Ah7n5h0jIvAbe4+7vx/ZvA5UD/mtY1syXu3iFpG4vdfb2mb2Z2DqE2CWBrYMJG5rU56QIsyHQiGkhLzhu07Py15LxBy85fS84btOz8teS8QcvOn/LWfLXk/LXkvCXr5+5dq5uRk8bKVs201IippmXSWbdW7v4g8OCGrNPcmdlodx+c6XQ0hJacN2jZ+WvJeYOWnb+WnDdo2flryXmDlp0/5a35asn5a8l5S1c6zd5mAH2S3vcGZqW5TG3rzo1N44h/56WfbBER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\n", "text/plain": [""]}, "metadata": {"needs_background": "light"}, "output_type": "display_data"}], "source": ["fig, ax = plt.subplots(1, 1, figsize=(14, 4))\n", "ax.bar(index, ave, align='center', color='orange')\n", "ax.set_xticks(index)\n", "ax.set_xticklabels(df100c.name)\n", "for tick in ax.get_xticklabels():\n", " tick.set_rotation(20)\n", "ax.errorbar(index, ave, \n", " numpy.abs((numpy.vstack([ave_min.values, ave_max.values]) - ave.values.ravel())),\n", " uplims=True, lolims=True)\n", "ax.set_title(\"Cumulated time spent in each node for 100 \"\n", " \"observations\\nGaussianProcess and onnxruntime1\");"]}, {"cell_type": "markdown", "metadata": {}, "source": ["The visual graph helps matching the output names with the operator type. The curve is not monotononic because each experiment computes every output from the start. The number of repetitions should be increased. Documentation of function [benchmark_fct](http://www.xavierdupre.fr/app/mlprodict/helpsphinx/mlprodict/onnxrt/validate/validate.html?highlight=benchmark_fct#mlprodict.onnxrt.validate.validate.benchmark_fct) tells how to do it."]}, {"cell_type": "code", "execution_count": 52, "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.7.2"}}, "nbformat": 4, "nbformat_minor": 2}