{ "cells": [ { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "<module 'waLBerla' from '/Users/holzer/walberla/python/waLBerla/__init__.py'>" ] }, "execution_count": 1, "metadata": {}, "output_type": "execute_result" } ], "source": [ "import pytest\n", "pytest.importorskip('waLBerla')" ] }, { "cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [], "source": [ "from pystencils.session import *\n", "from time import perf_counter\n", "from statistics import median\n", "from functools import partial" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Benchmark for Python call overhead" ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/latex": [ "$\\displaystyle \\left[ 2, \\ 4, \\ 8, \\ 16, \\ 32, \\ 64, \\ 128\\right]$" ], "text/plain": [ "[2, 4, 8, 16, 32, 64, 128]" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "inner_repeats = 100\n", "outer_repeats = 5\n", "sizes = [2**i for i in range(1, 8)]\n", "sizes" ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [], "source": [ "def benchmark_pure(domain_size, extract_first=False):\n", " src = np.zeros(domain_size)\n", " dst = np.zeros_like(src)\n", " f_src, f_dst = ps.fields(\"src, dst\", src=src, dst=dst)\n", " kernel = ps.create_kernel(ps.Assignment(f_dst.center, f_src.center)).compile()\n", " if extract_first:\n", " kernel = kernel.kernel\n", " start = perf_counter()\n", " for i in range(inner_repeats):\n", " kernel(src=src, dst=dst)\n", " src, dst = dst, src\n", " end = perf_counter()\n", " else:\n", " start = perf_counter()\n", " for i in range(inner_repeats):\n", " kernel(src=src, dst=dst)\n", " src, dst = dst, src\n", " end = perf_counter()\n", " return (end - start) / inner_repeats\n", "\n", "def benchmark_datahandling(domain_size, parallel=False):\n", " dh = ps.create_data_handling(domain_size, parallel=parallel)\n", " f_src = dh.add_array('src')\n", " f_dst = dh.add_array('dst')\n", " kernel = ps.create_kernel(ps.Assignment(f_dst.center, f_src.center)).compile()\n", " start = perf_counter()\n", " for i in range(inner_repeats):\n", " dh.run_kernel(kernel)\n", " dh.swap('src', 'dst')\n", " end = perf_counter()\n", " return (end - start) / inner_repeats\n", " \n", " \n", "name_to_func = {\n", " 'pure_extract': partial(benchmark_pure, extract_first=True),\n", " 'pure_no_extract': partial(benchmark_pure, extract_first=False),\n", " 'dh_serial': partial(benchmark_datahandling, parallel=False),\n", " 'dh_parallel': partial(benchmark_datahandling, parallel=True),\n", "}" ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Computing size 2\n" ] }, { "ename": "ValueError", "evalue": "Cannot create parallel data handling because walberla module is not available", "output_type": "error", "traceback": [ "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", "\u001b[0;31mValueError\u001b[0m Traceback (most recent call last)", "\u001b[0;32m/var/folders/07/0d7kq8fd0sx24cs53zz90_qc0000gp/T/ipykernel_12649/2009975470.py\u001b[0m in \u001b[0;36m<module>\u001b[0;34m\u001b[0m\n\u001b[1;32m 7\u001b[0m \u001b[0;32mfor\u001b[0m \u001b[0mname\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mfunc\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mname_to_func\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mitems\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 8\u001b[0m \u001b[0;32mfor\u001b[0m \u001b[0mi\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mrange\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mouter_repeats\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m----> 9\u001b[0;31m \u001b[0mtime\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mfunc\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mbs\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mbs\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 10\u001b[0m \u001b[0mresult\u001b[0m\u001b[0;34m[\u001b[0m\u001b[0;34m'block_size'\u001b[0m\u001b[0;34m]\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mappend\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mbs\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 11\u001b[0m \u001b[0mresult\u001b[0m\u001b[0;34m[\u001b[0m\u001b[0;34m'name'\u001b[0m\u001b[0;34m]\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mappend\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mname\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n", "\u001b[0;32m/var/folders/07/0d7kq8fd0sx24cs53zz90_qc0000gp/T/ipykernel_12649/3509370390.py\u001b[0m in \u001b[0;36mbenchmark_datahandling\u001b[0;34m(domain_size, parallel)\u001b[0m\n\u001b[1;32m 20\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 21\u001b[0m \u001b[0;32mdef\u001b[0m \u001b[0mbenchmark_datahandling\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdomain_size\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mparallel\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0;32mFalse\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 22\u001b[0;31m \u001b[0mdh\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mps\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mcreate_data_handling\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdomain_size\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mparallel\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0mparallel\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 23\u001b[0m \u001b[0mf_src\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mdh\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0madd_array\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m'src'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 24\u001b[0m \u001b[0mf_dst\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mdh\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0madd_array\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m'dst'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n", "\u001b[0;32m~/pystencils/pystencils/pystencils/datahandling/__init__.py\u001b[0m in \u001b[0;36mcreate_data_handling\u001b[0;34m(domain_size, periodicity, default_layout, default_target, parallel, default_ghost_layers)\u001b[0m\n\u001b[1;32m 44\u001b[0m \u001b[0;32mif\u001b[0m \u001b[0mparallel\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 45\u001b[0m \u001b[0;32mif\u001b[0m \u001b[0mwlb\u001b[0m \u001b[0;32mis\u001b[0m \u001b[0;32mNone\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 46\u001b[0;31m \u001b[0;32mraise\u001b[0m \u001b[0mValueError\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m\"Cannot create parallel data handling because walberla module is not available\"\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 47\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 48\u001b[0m \u001b[0;32mif\u001b[0m \u001b[0mperiodicity\u001b[0m \u001b[0;32mis\u001b[0m \u001b[0;32mFalse\u001b[0m \u001b[0;32mor\u001b[0m \u001b[0mperiodicity\u001b[0m \u001b[0;32mis\u001b[0m \u001b[0;32mNone\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n", "\u001b[0;31mValueError\u001b[0m: Cannot create parallel data handling because walberla module is not available" ] } ], "source": [ "result = {'block_size': [],\n", " 'name': [],\n", " 'time': []}\n", "\n", "for bs in sizes:\n", " print(\"Computing size \", bs)\n", " for name, func in name_to_func.items():\n", " for i in range(outer_repeats):\n", " time = func((bs, bs))\n", " result['block_size'].append(bs)\n", " result['name'].append(name)\n", " result['time'].append(time)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "if 'is_test_run' not in globals():\n", " import pandas as pd\n", " import seaborn as sns\n", " \n", " data = pd.DataFrame.from_dict(result)\n", "\n", " plt.subplot(1,2,1)\n", " sns.barplot(x='block_size', y='time', hue='name', data=data, alpha=0.6)\n", " plt.yscale('log')\n", "\n", " plt.subplot(1,2,2)\n", " data = pd.DataFrame.from_dict(result)\n", " sns.barplot(x='block_size', y='time', hue='name', data=data, alpha=0.6)" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3 (ipykernel)", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.9.9" } }, "nbformat": 4, "nbformat_minor": 2 }