{ "cells": [ { "cell_type": "markdown", "metadata": { "collapsed": true }, "source": [ "# SymPyで代数と式を計算する\n", "## 式の記号と記号演算を定義する" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$2x + 1$\n", "\n", "$2xy$\n", "\n", "$2x^2$ \n", "\n", "$(x+2)(y+3)$" ] }, { "cell_type": "code", "execution_count": 4, "metadata": { "collapsed": true }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Collecting sympy\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ " Using cached https://files.pythonhosted.org/packages/dd/f6/ed485ff22efdd7b371d0dbbf6d77ad61c3b3b7e0815a83c89cbb38ce35de/sympy-1.3.tar.gz\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Collecting mpmath>=0.19 (from sympy)\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ " Using cached https://files.pythonhosted.org/packages/7a/05/b3d1472885d8dc0606936ea5da0ccb1b4785682e78ab15e34ada24aea8d5/mpmath-1.0.0.tar.gz\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Building wheels for collected packages: sympy, mpmath\r\n Running setup.py bdist_wheel for sympy ... \u001b[?25l" ] }, { "name": "stdout", "output_type": "stream", "text": [ "-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b|" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b/" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b|" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b/" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b|" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b/" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b|" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b/" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b|" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b/" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \bdone\r\n\u001b[?25h Stored in directory: /Users/k2works/Library/Caches/pip/wheels/6c/59/86/478e3c0f298368c119095cc5985dedac57c0e35a85c737f823\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ " Running setup.py bdist_wheel for mpmath ... \u001b[?25l" ] }, { "name": "stdout", "output_type": "stream", "text": [ "-" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \b\\" ] }, { "name": "stdout", "output_type": "stream", "text": [ "\b \bdone\r\n\u001b[?25h Stored in directory: /Users/k2works/Library/Caches/pip/wheels/33/15/0f/9ca5f2ad88a5456803098daa189f382408a81556aa209e97ff\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Successfully built sympy mpmath\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Installing collected packages: mpmath, sympy\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Successfully installed mpmath-1.0.0 sympy-1.3\r\n" ] } ], "source": [ "import sys\n", "!{sys.executable} -m pip install sympy" ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 5 tests in 0.004s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol\n", "from sympy import symbols\n", "\n", "\n", "class TestSymPy(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " expect = x + x + 1\n", " self.assertEqual(expect, 2 * x + 1)\n", "\n", " def test_02(self):\n", " a = Symbol('x')\n", " expect = a + a + 1\n", " self.assertEqual(expect, 2 * a + 1)\n", "\n", " def test_03(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " s = x * y + x * y\n", " self.assertEqual(s, 2 * x * y)\n", "\n", " def test_04(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " p = x * (x + x)\n", " self.assertEqual(p, 2 * x ** 2)\n", "\n", " x, y = symbols('x,y')\n", " p = x * (x + x)\n", " self.assertEqual(p, 2 * x ** 2)\n", "\n", " def test_05(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " p = (x + 2) * (x + 3)\n", " self.assertEqual(p, (x + 2) * (x + 3))\n", "\n", " x, y = symbols('x,y')\n", " p = (x + 2) * (x + 3)\n", " self.assertEqual(p, (x + 2) * (x + 3))\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## 式を扱う\n", "### 式の因数分解と展開" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$x^2-y^2$ = $(x-y)(x+y)$\n", "\n", "$x3 + 3x^2y + 3xy^2 + y^3$ = $(x + y)^3$\n", "\n", "$x + y + xy$ = $xy + x + y$" ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 4 tests in 0.013s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol\n", "from sympy import factor, expand\n", "\n", "\n", "class TestSymPy(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x ** 2 - y ** 2\n", " self.assertEqual(factor(expr), (x - y) * (x + y))\n", " \n", " def test_02(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x**2 - y**2\n", " factors = factor(expr)\n", " self.assertEqual(expand(factors), x**2 - y**2)\n", " \n", " def test_03(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x**3 + 3*x**2*y + 3*x*y**2 + y**3\n", " factors = factor(expr)\n", " self.assertEqual(factors,(x + y)**3)\n", " self.assertEqual(expand(factors),x**3 + 3*x**2*y + 3*x*y**2 + y**3)\n", "\n", " def test_04(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x + y + x*y\n", " self.assertEqual(factor(expr), x*y + x + y)\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### プリティプリント" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$x^2 + 2xy + y^2$\n", "\n", "$2x^2 + 2x + 1$\n", "\n", "$1 + 2x + 2x^2$" ] }, { "cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "x**2 + 2*x*y + y**2\n 2 2\nx + 2⋅x⋅y + y \n 2 \n2⋅x + 2⋅x + 1\n 2 \n2⋅x + 2⋅x + 1\n" ] } ], "source": [ "from sympy import Symbol\n", "from sympy import pprint\n", "from sympy import init_printing\n", "\n", "if __name__ == '__main__':\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x*x + 2*x*y + y*y\n", " print(expr)\n", " pprint(expr, use_unicode=True)\n", " expr = 1 + 2*x + 2*x**2\n", " pprint(expr, use_unicode=True)\n", " init_printing(order='rev-lex')\n", " pprint(expr, use_unicode=True)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### 級数を出力する" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$x + \\frac{x^2}{2} + \\frac{x^3}{3} + \\frac{x^4}{4} + ... + \\frac{x^n}{n}$" ] }, { "cell_type": "code", "execution_count": 16, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stdout", "output_type": "stream", "text": [ "x\n 2 \nx \n── + x\n2 \n 3 2 \nx x \n── + ── + x\n3 2 \n 4 3 2 \nx x x \n── + ── + ── + x\n4 3 2 \n" ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 5 tests in 0.028s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol, pprint, init_printing\n", "\n", "'''\n", "級数を出力\n", "x + x**2 + x**3 + ... + x**n\n", " --- --- ---\n", " 2 3 n\n", "xの値で級数の値を計算\n", "'''\n", "def print_series(n):\n", " # 出力を逆順に初期化\n", " init_printing(order='rev-lex')\n", " x = Symbol('x')\n", " series = x\n", " for i in range(2, n + 1):\n", " series = series + (x ** i) / i\n", " pprint(series)\n", " return series\n", "\n", "\n", "class TestPrintSeries(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " self.assertEqual(print_series(1), x)\n", " self.assertEqual(print_series(2), x ** 2 / 2 + x)\n", " self.assertEqual(print_series(3), x ** 3 / 3 + x ** 2 / 2 + x)\n", " self.assertEqual(print_series(4), x ** 4 / 4 + x ** 3 / 3 + x ** 2 / 2 + x)\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 値に代入する" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "\n", "$xx + xy + xy + yy$ \n", "\n", "$x = 1, y = 2$ \n", "\n", "$9$ \n", "\n", "$x = y - 1$\n", "\n", "$y^2 + 2y(-y + 1)+(-y + 1)^2$ \n", "\n", "$y^2 - 2y^2 + 2y + y^2 -2y + 1$ \n", "\n", "$1$" ] }, { "cell_type": "code", "execution_count": 17, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stdout", "output_type": "stream", "text": [ "x\n 2 \nx \n── + x\n2 \n 3 2 \nx x \n── + ── + x\n3 2 \n 4 3 2 \nx x x \n── + ── + ── + x\n4 3 2 \n" ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 4 tests in 0.031s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol\n", "from sympy import factor, expand, simplify\n", "\n", "\n", "class TestSymPy(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x * x + x * y + x * y + y * y\n", " self.assertEqual(expr.subs({x: 1, y: 2}), 9)\n", "\n", " def test_02(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x * x + x * y + x * y + y * y\n", " self.assertEqual(expr.subs({x: 1 - y}), y ** 2 + 2 * y * (-y + 1) + (-y + 1) ** 2)\n", "\n", " def test_03(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr = x * x + x * y + x * y + y * y\n", " expr_subs = expr.subs({x: 1 - y})\n", " self.assertEqual(simplify(expr_subs), 1)\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### 級数の値を計算する" ] }, { "cell_type": "code", "execution_count": 18, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stdout", "output_type": "stream", "text": [ " 5 4 3 2 \nx x x x \n── + ── + ── + ── + x\n5 4 3 2 \nValue of the series at 12: 278052/5\n" ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 4 tests in 0.015s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol, pprint, init_printing\n", "\n", "\n", "def print_series(n, x_value):\n", " # 出力を逆順に初期化\n", " init_printing(order='rev-lex')\n", " x = Symbol('x')\n", " series = x\n", " for i in range(2, n+1):\n", " series = series + (x**i)/i\n", " pprint(series)\n", "\n", " # x_valueで級数評価\n", " series_value = series.subs({x:x_value})\n", " print('Value of the series at {0}: {1}'.format(x_value, series_value))\n", " return series_value\n", "\n", "\n", "class TestPrintSeries(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " self.assertEqual(print_series(5,12), 278052/5)\n", " \n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 文字列を数式に変換する" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### 数式乗算器" ] }, { "cell_type": "code", "execution_count": 19, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stdout", "output_type": "stream", "text": [ " 5 4 3 2 \nx x x x \n── + ── + ── + ── + x\n5 4 3 2 \nValue of the series at 12: 278052/5\nx**5 + 3*x**4 + 4*x**3 + 12*x**2\nx**3*y + x**3 + x*y**2 + x*y\n" ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 6 tests in 0.020s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol, expand, sympify\n", "from sympy.core.sympify import SympifyError\n", "\n", "'''\n", "2式の積\n", "'''\n", "def product(expr1, expr2):\n", " try:\n", " expr1 = sympify(expr1)\n", " expr2 = sympify(expr2)\n", " except SympifyError:\n", " print('Invalid input')\n", " else:\n", " prod = expand(expr1 * expr2)\n", " print(prod)\n", " return prod\n", "\n", "\n", "class TestProduct(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " expr1 = x ** 2 + x * 2 + x\n", " expr2 = x ** 3 + x * 3 + x\n", " self.assertEqual(product(expr1, expr2), x ** 5 + 3 * x ** 4 + 4 * x ** 3 + 12 * x ** 2)\n", " \n", " def test_02(self):\n", " x = Symbol('x')\n", " y = Symbol('y')\n", " expr1 = x*y+x\n", " expr2 = x*x+y\n", " self.assertEqual(product(expr1, expr2), x**3*y + x**3 + x*y**2 + x*y)\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## 方程式を解く" ] }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stdout", "output_type": "stream", "text": [ " 5 4 3 2 \nx x x x \n── + ── + ── + ── + x\n5 4 3 2 \nValue of the series at 12: 278052/5\nx**5 + 3*x**4 + 4*x**3 + 12*x**2\nx**3*y + x**3 + x*y**2 + x*y\n" ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 4 tests in 0.012s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol, solve\n", "\n", "class TestSolve(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " expr = x - 5 - 7\n", " self.assertEqual(solve(expr), [12])\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 2次方程式を解く" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$x^2 + 5^x + 4$ \n", "\n", "$x^2 + x + 1$" ] }, { "cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stderr", "output_type": "stream", "text": [ "." ] }, { "name": "stdout", "output_type": "stream", "text": [ " 5 4 3 2 \nx x x x \n── + ── + ── + ── + x\n5 4 3 2 \nValue of the series at 12: 278052/5\nx**5 + 3*x**4 + 4*x**3 + 12*x**2\nx**3*y + x**3 + x*y**2 + x*y\n⎡⎧ 1 √3⋅ⅈ⎫ ⎧ 1 √3⋅ⅈ⎫⎤\n⎢⎨x: - ─ - ────⎬, ⎨x: - ─ + ────⎬⎥\n⎣⎩ 2 2 ⎭ ⎩ 2 2 ⎭⎦\n" ] }, { "name": "stderr", "output_type": "stream", "text": [ "\n----------------------------------------------------------------------\nRan 5 tests in 0.080s\n\nOK\n" ] } ], "source": [ "import unittest\n", "from sympy import Symbol, solve, pprint\n", "\n", "\n", "class TestSolve(unittest.TestCase):\n", " def test_01(self):\n", " x = Symbol('x')\n", " expr = x ** 2 + 5 * x + 4\n", " self.assertEqual(solve(expr), [-4, -1])\n", " self.assertEqual(solve(expr, dict=True), [{x: -4}, {x: -1}])\n", " \n", " def test_02(self):\n", " x = Symbol('x')\n", " expr = x**2 + x + 1\n", " pprint(solve(expr, dict=True))\n", "\n", "\n", "if __name__ == '__main__':\n", " unittest.main(argv=['first-arg-is-ignored'], exit=False)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 1変数を他の変数について解く" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$s = ut + \\frac{1}{2}att$ \n", "\n", "$t:\\frac{1}{a}(-u+\\sqrt{2.0as + u^2})$ \n", "\n", "$t:-\\frac{1}{a}(-u+\\sqrt{2.0as + u^2})$" ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "⎡⎧ ______________⎫ ⎧ ⎛ ______________⎞ ⎫⎤\n⎢⎪ ╱ 2 ⎪ ⎪ ⎜ ╱ 2 ⎟ ⎪⎥\n⎢⎨ -u + ╲╱ 2.0⋅a⋅s + u ⎬ ⎨ -⎝u + ╲╱ 2.0⋅a⋅s + u ⎠ ⎬⎥\n⎢⎪t: ──────────────────────⎪, ⎪t: ─────────────────────────⎪⎥\n⎣⎩ a ⎭ ⎩ a ⎭⎦\n" ] } ], "source": [ "from sympy import Symbol, solve, pprint\n", "\n", "s = Symbol('s')\n", "u = Symbol('u')\n", "t = Symbol('t')\n", "a = Symbol('a')\n", "expr = u*t + (1/2)*a*t*t - s\n", "t_expr = solve(expr, t, dict=True)\n", "pprint(t_expr)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 連立方程式を解く" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$2x + 3y = 6$ \n", "\n", "$3x + 2y = 12$" ] }, { "cell_type": "code", "execution_count": 15, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[{x: 24/5, y: -6/5}]\n0\n0\n" ] } ], "source": [ "from sympy import Symbol, solve, pprint\n", "\n", "x = Symbol('x')\n", "y = Symbol('y')\n", "expr1 = 2 * x + 3 * y - 6\n", "expr2 = 3 * x + 2 * y - 12\n", "soln = solve((expr1, expr2), dict=True)\n", "print(soln)\n", "soln = soln[0]\n", "expr1 = expr1.subs({x: soln[x], y: soln[y]})\n", "print(expr1)\n", "expr2 = expr2.subs({x: soln[x], y: soln[y]})\n", "print(expr2)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## SymPyを使ってプロットする" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$y = 2x+3$" ] }, { "cell_type": "code", "execution_count": 20, "metadata": { "collapsed": true }, "outputs": [ { "data": { "text/plain": [ "" ] }, "execution_count": 20, "metadata": {}, "output_type": "execute_result" } ], "source": [ "from sympy.plotting import plot\n", "from sympy import Symbol\n", "\n", "x = Symbol('x')\n", "plot(2*x*3)\n", "plot((2*x + 3),(x, -5, 5))\n", "plot(2*x + 3,(x, -5, 5), title='A Line', xlabel='x', ylabel='2x+3')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### ユーザが入力した式をプロットする" ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [ { "ename": "ModuleNotFoundError", "evalue": "No module named 'sympy'", "traceback": [ "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", "\u001b[0;31mModuleNotFoundError\u001b[0m Traceback (most recent call last)", "\u001b[0;32m\u001b[0m in \u001b[0;36m\u001b[0;34m()\u001b[0m\n\u001b[0;32m----> 1\u001b[0;31m \u001b[0;32mfrom\u001b[0m \u001b[0msympy\u001b[0m \u001b[0;32mimport\u001b[0m \u001b[0mSymbol\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0msympify\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0msolve\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 2\u001b[0m \u001b[0;32mfrom\u001b[0m \u001b[0msympy\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mplotting\u001b[0m \u001b[0;32mimport\u001b[0m \u001b[0mplot\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 3\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 4\u001b[0m \u001b[0;32mdef\u001b[0m \u001b[0mplot_expression\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mexpr\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 5\u001b[0m \u001b[0my\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mSymbol\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m'y'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n", "\u001b[0;31mModuleNotFoundError\u001b[0m: No module named 'sympy'" ], "output_type": "error" } ], "source": [ "from sympy import Symbol, sympify, solve\n", "from sympy.plotting import plot\n", "\n", "def plot_expression(expr):\n", " y = Symbol('y')\n", " solutions = solve(expr, y)\n", " expr_y = solutions[0]\n", " plot(expr_y)\n", " \n", " \n", "if __name__ == '__main__':\n", " \n", " expr = input('Enter your expression in terms of x and y: ')\n", " try:\n", " expr = sympify(expr)\n", " except SympifyError:\n", " print('Invalid input')\n", " else:\n", " plot_expression(expr)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 複数の関数をプロットする" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "$y=2x+3$ \n", "\n", "$y=3x+1$" ] }, { "cell_type": "code", "execution_count": 25, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "text/plain": [ "" ] }, "execution_count": 25, "metadata": {}, "output_type": "execute_result" } ], "source": [ "from sympy.plotting import plot\n", "from sympy import Symbol\n", "x = Symbol('x')\n", "plot(2*x+3, 3*x+1)" ] }, { "cell_type": "code", "execution_count": 22, "metadata": {}, "outputs": [], "source": [ "from sympy.plotting import plot\n", "from sympy import Symbol\n", "x = Symbol('x')\n", "p = plot(2*x+3, 3*x+1, lengend=True, show=False)\n", "p[0].line_color = 'b'\n", "p[1].line_color = 'r'\n", "p.show()" ] } ], "metadata": { "kernelspec": { "display_name": "Python 2", "language": "python", "name": "python2" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 2 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython2", "version": "2.7.6" } }, "nbformat": 4, "nbformat_minor": 0 }