{ "cells": [ { "cell_type": "markdown", "id": "b40cde8e-a20e-4904-bfec-753a7d82a300", "metadata": {}, "source": [ "# How to discretize equations \n", "\n", "Now we demonstrate how to discretize a PDE object.\n", "\n", "Pre-coded sample objects are stored in `sample` attribute of *phyem*. Invoke these samples by" ] }, { "cell_type": "code", "execution_count": 1, "id": "d603a38d-c76a-4cf6-b5fc-bbd27c54db4f", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:57.387182Z", "iopub.status.busy": "2024-11-28T03:41:57.387182Z", "iopub.status.idle": "2024-11-28T03:41:58.651258Z", "shell.execute_reply": "2024-11-28T03:41:58.651258Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "import sys\n", "ph_dir = '../../../../../' # the path to dir that containing the phyem package.\n", "sys.path.append(ph_dir)\n", "import phyem as ph # import the phyem package\n", "ph.config._set_matplot_block(False)\n", "samples = ph.samples" ] }, { "cell_type": "markdown", "id": "498e0ee3-b788-4265-81a9-ce957c466895", "metadata": {}, "source": [ "The partial differential equations of the canocical linear por-Hamiltonian are pre-coded. Call it through" ] }, { "cell_type": "code", "execution_count": 2, "id": "a343b362-5677-42d7-8dc2-cdb3cca95e45", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:58.767724Z", "iopub.status.busy": "2024-11-28T03:41:58.767724Z", "iopub.status.idle": "2024-11-28T03:41:58.770716Z", "shell.execute_reply": "2024-11-28T03:41:58.770716Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "oph = samples.pde_canonical_pH(n=3, p=3, periodic=True)[0] # where o on `oph` means outer" ] }, { "cell_type": "markdown", "id": "702b2712-bd83-468e-9478-3e9c608d1a55", "metadata": {}, "source": [ "Check `oph`, *outer oriented port-Hamiltonian*, with" ] }, { "cell_type": "code", "execution_count": 3, "id": "8fd0eb4d-6350-4268-a3a3-c905926b46a4", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:58.800932Z", "iopub.status.busy": "2024-11-28T03:41:58.800932Z", "iopub.status.idle": "2024-11-28T03:41:59.238138Z", "shell.execute_reply": "2024-11-28T03:41:59.238138Z" }, "is_executing": true, "tags": [] }, "outputs": [ { "data": { "text/plain": [ "<Figure size 800x600 with 1 Axes>" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "oph.pr()" ] }, { "cell_type": "markdown", "id": "95eaceec-a95e-4da5-82c7-7e7b1a8770a5", "metadata": {}, "source": [ "We can take out the knowns and label them by" ] }, { "cell_type": "code", "execution_count": 4, "id": "6bb4c1e9-e284-4de6-bf5a-746a707fb08f", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:59.315376Z", "iopub.status.busy": "2024-11-28T03:41:59.314309Z", "iopub.status.idle": "2024-11-28T03:41:59.317308Z", "shell.execute_reply": "2024-11-28T03:41:59.317308Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "a3, b2 = oph.unknowns" ] }, { "cell_type": "markdown", "id": "4c0f26a4-49b6-4d3c-aca3-e355f35449c9", "metadata": {}, "source": [ "We now test `oph` with test functions from the spaces where `a3` and `b2` come from, and label the test functions by $v^3$ and $u^2$," ] }, { "cell_type": "code", "execution_count": 5, "id": "01e41ea7-fbd8-4e0a-80e0-771bd1498ded", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:59.345538Z", "iopub.status.busy": "2024-11-28T03:41:59.345538Z", "iopub.status.idle": "2024-11-28T03:41:59.348954Z", "shell.execute_reply": "2024-11-28T03:41:59.348954Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "wf = oph.test_with(oph.unknowns, sym_repr=[r'v^3', r'u^2'])" ] }, { "cell_type": "markdown", "id": "a627673d-fbaa-4b35-9f4b-7184f265d382", "metadata": { "tags": [] }, "source": [ "Now, we apply integration by parts to the term indexed by `'1-1'`." ] }, { "cell_type": "code", "execution_count": 6, "id": "fec1529c-8a7a-4b5a-9e4c-0c4580f06729", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:59.377659Z", "iopub.status.busy": "2024-11-28T03:41:59.377659Z", "iopub.status.idle": "2024-11-28T03:41:59.380746Z", "shell.execute_reply": "2024-11-28T03:41:59.380746Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "wf = wf.derive.integration_by_parts('1-1')" ] }, { "cell_type": "markdown", "id": "65b936bb-c33f-4a14-a0cc-c67ae5d1c00f", "metadata": { "tags": [] }, "source": [ "We now apply a particular discretization to this weak formulation," ] }, { "cell_type": "code", "execution_count": 7, "id": "99d09aa1-ef0f-48ae-b104-bb128fd380bb", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:59.409431Z", "iopub.status.busy": "2024-11-28T03:41:59.409431Z", "iopub.status.idle": "2024-11-28T03:41:59.416556Z", "shell.execute_reply": "2024-11-28T03:41:59.416556Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "td = wf.td\n", "td.set_time_sequence() # initialize a time sequence\n", "td.define_abstract_time_instants('k-1', 'k-1/2', 'k')\n", "td.differentiate('0-0', 'k-1', 'k')\n", "td.average('0-1', b2, ['k-1', 'k'])\n", "\n", "td.differentiate('1-0', 'k-1', 'k')\n", "td.average('1-1', a3, ['k-1', 'k'])\n", "dt = td.time_sequence.make_time_interval('k-1', 'k')\n", "\n", "wf = td()\n", "\n", "wf.unknowns = [\n", " a3 @ td.time_sequence['k'],\n", " b2 @ td.time_sequence['k'],\n", "]\n", "\n", "wf = wf.derive.split(\n", " '0-0', 'f0',\n", " [a3 @ td.ts['k'], a3 @ td.ts['k-1']],\n", " ['+', '-'],\n", " factors=[1/dt, 1/dt],\n", ")\n", "\n", "wf = wf.derive.split(\n", " '0-2', 'f0',\n", " [ph.d(b2 @ td.ts['k-1']), ph.d(b2 @ td.ts['k'])],\n", " ['+', '+'],\n", " factors=[1/2, 1/2],\n", ")\n", "\n", "wf = wf.derive.split(\n", " '1-0', 'f0',\n", " [b2 @ td.ts['k'], b2 @ td.ts['k-1']],\n", " ['+', '-'],\n", " factors=[1/dt, 1/dt]\n", ")\n", "\n", "wf = wf.derive.split(\n", " '1-2', 'f0',\n", " [a3 @ td.ts['k-1'], a3 @ td.ts['k']],\n", " ['+', '+'],\n", " factors=[1/2, 1/2],\n", ")\n", "\n", "wf = wf.derive.rearrange(\n", " {\n", " 0: '0, 3 = 2, 1',\n", " 1: '3, 0 = 2, 1',\n", " }\n", ")" ] }, { "cell_type": "markdown", "id": "a0de472f-32b1-4c27-93cc-0abe5cbab7b9", "metadata": {}, "source": [ "We now can write the weak formulation with matrix proxies. Before doing that, we need to " ] }, { "cell_type": "code", "execution_count": 8, "id": "5e30efae-221f-4969-b285-243686f4c1f9", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:59.455344Z", "iopub.status.busy": "2024-11-28T03:41:59.455344Z", "iopub.status.idle": "2024-11-28T03:41:59.460313Z", "shell.execute_reply": "2024-11-28T03:41:59.460313Z" }, "is_executing": true, "tags": [] }, "outputs": [], "source": [ "ph.space.finite(3)\n", "mp = wf.mp()" ] }, { "cell_type": "markdown", "id": "2bf04ccc-e555-4eed-9eae-3dc55f1ac324", "metadata": {}, "source": [ "The matrix format of the weak formulation leads to a linear system," ] }, { "cell_type": "code", "execution_count": 9, "id": "7bffe47c-a9bd-4bcf-95e8-f8ccf14a0ada", "metadata": { "execution": { "iopub.execute_input": "2024-11-28T03:41:59.486018Z", "iopub.status.busy": "2024-11-28T03:41:59.486018Z", "iopub.status.idle": "2024-11-28T03:41:59.573818Z", "shell.execute_reply": "2024-11-28T03:41:59.573818Z" }, "is_executing": true, "tags": [] }, "outputs": [ { "data": { "text/plain": [ "<Figure size 1200x600 with 1 Axes>" ] }, "execution_count": 9, "metadata": {}, "output_type": "execute_result" } ], "source": [ "ls = mp.ls()\n", "ls.pr()" ] }, { "cell_type": "markdown", "id": "ba265f8a-8b4f-4704-af51-2e9cc45a222c", "metadata": {}, "source": [ "Note that, till this moment, everything is still abstract. To do the numerical simulation, we need to bring them to a particular implementation, for example, the `msepy`, standing for *mimetic spectral elements python*, by calling `ph.fem.apply` function, which will be shown in other notebooks." ] } ], "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.12.7" } }, "nbformat": 4, "nbformat_minor": 5 }