第4回:▼ 不連続な曲線を描く

■ plot関数のフォーマット・パラメータ

PyPlot パッケージに含まれる関数plotは、 複数回起動する毎に曲線の見た目を変える。

見た目を個別に変えるには、plot 関数のデータを指定した直後に、 文字列(fmt パラメータ) を指定する。

fmtパラメータは、 色、マーカー種類、線の見た目を、1文字ないし2文字で指定する。 指定しなければ、規定値が選ばれる。

色を変える例

using PyPlot
xs=-10:0.1:10
plt.plot(xs, 9.0.^xs, "b", label="b") # blue
plt.plot(xs, 8.0.^xs, "g", label="g") # green
plt.plot(xs, 7.0.^xs, "r", label="r") # red
plt.plot(xs, 6.0.^xs, "c", label="c") # cyan
plt.plot(xs, 5.0.^xs, "m", label="m") # magenda
plt.plot(xs, 4.0.^xs, "y", label="y") # yellow
plt.plot(xs, 3.0.^xs, "k", label="k") # black
plt.plot(xs, 2.0.^xs, "w", label="w") # white (白背景では見えない)
plt.xlim(0,3)
plt.ylim(0,100)
plt.legend()

マーカーの形を変える例。 マーカーの色は全て青とした

using PyPlot
xs=-2:0.2:2
ys=xs.^2
plt.plot(xs, ys,      "b.", label=".") # point
plt.plot(xs, ys .-2,  "b,", label=",") # pixel
plt.plot(xs, ys .-4,  "bo", label="o") # circle
plt.plot(xs, ys .-6,  "bs", label="s") # square
plt.plot(xs, ys .-8,  "b*", label="*") # star
plt.plot(xs, ys .-10, "b+", label="+") # plus
plt.plot(xs, ys .-12, "bx", label="x") # x
plt.plot(xs, ys .-14, "bD", label="D") # diamond
plt.plot(xs, ys .-16, "bd", label="d") # thin diamond
plt.xlim(-3,3)
plt.legend()

線のスタイルを変える例

using PyPlot
xs=-2:0.2:2
ys=xs.^3-xs.^2
plt.plot(xs, ys .-0, "r-",  label="-")  # solid line
plt.plot(xs, ys .-2, "r--", label="--") # dashed line
plt.plot(xs, ys .-4, "r-.", label="-.") # dash-dot line
plt.plot(xs, ys .-6, "r:",  label=":")  # dotted line plt.xlim(-2.2,2.2)
plt.legend()

■ 0による除算

筆算では 0による除算の結果は未定義である。

Julia では、0による除算は、例外は発生せず、 「数でない数」 Inf, -Inf, NaN のどれかが得られる。

Inf は、無限大 Infinity に由来する。 NaN は、数でない Not a Number に由来する。

julia> 1 / 0
Inf

julia> -1 / 0
-Inf

julia> 0 / 0
NaN

▼ 関数が連続とは

関数が連続であるとは、 関数のグラフがつながっている,ちぎれていないことをいう。

「関数 $f(x)$$x=a$ で連続」とは、

\[\lim_{x \longrightarrow a} f(x)\]

が存在して、その値が $f(a)$ に等しいと定義される。

不連続とは、連続でないことである。 ただし、不連続な関数でも、連続な部分があることが多く、 それらを、枝 (branch) という。

この章では、主に、連続ではない関数のグラフを描く。

▼ 逆数関数を描く

逆数関数 $y=\dfrac{1}{x}$ を描いてみよう。

Note

逆数関数 reciprocal function という。逆関数 inverse function と区別されたい。

さて、$\dfrac{1}{0}$の値はInfであるが、plot関数は「数でない数」をスキップして何も描かない。分母 $0$ の除算を特別扱いする必要はない。

逆数関数は、$x=0$ で不連続であり、$x$の正負に対応して二つの枝を持つ。

using PyPlot
plt.axes().set_aspect("equal")
xs=-3:0.1:3
plt.plot(xs,1.0 ./xs)
plt.xlim(-3,3)
plt.ylim(-3,3)

続けて、$y=x$$y=-x$、水平線 $y = 0$、垂直線 $x = 0$、を追加しよう。

plt.plot(xs,xs, color="k", lw=0.5)
plt.plot(xs,-1*xs, color="k", lw=0.5)
plt.axhline(0, color="k", lw=0.5)
plt.axvline(0, color="k", lw=0.5)

▲ 練習

(プログラミングでなく、数学の話題)

数学では「何らかの操作を行った結果が、元と重なること」を、 その操作に対して対称である(symmetric)という。

上のグラフを観察すると、逆数関数は、いくつかの操作に対して対称であることがわかる。どのような操作か?

▼ 不連続な有理式を描く

有理関数とは、多項式(分子)を多項式(分母)で割った関数である。

以下の有理関数を描こう。

\[y = \dfrac{x^3+8}{x^3+3x^2-4x-12}\]

まず、分母を描く。

using PyPlot
xs=-10:0.1:10
qs= xs.^3 .+ 3xs.^2 .- 4xs .-12
plt.plot(xs, qs)
plt.ylim(-20,20)
plt.xlim(-4,4)
plt.axhline(0, color="k", lw=0.5)
plt.axvline(-3, color="k", lw=0.5)
plt.axvline(-2, color="k", lw=0.5)
plt.axvline(2, color="k", lw=0.5)

分母は $x=-3, -2, 2$$0$ となるから、 上の有理関数は、この三点で不連続となる「可能性」がある。

では、上の有理関数を描いてみる。 逆数関数の描画と同じように、分母 $0$ となる場合を特別扱いする必要はない。

xs=-10:0.05:10
ps= xs.^3 .+ 8
qs= xs.^3 .+ 3xs.^2 .- 4xs .-12
ys= ps ./ qs
plt.plot(xs, ys)
plt.ylim(-10,10)
plt.xlim(-4,4)
plt.axhline(0, color="k", lw=0.5)
plt.axvline(-3, color="k", lw=0.5)
plt.axvline(2, color="k", lw=0.5)

実際には、$x=-2$ では不連続ではない。 分子・分母を共通項 $(x+2)$ で割れるからである。

もう少し、横軸の範囲を狭めて描く。

xs=-10:0.05:10
ps= xs.^3 .+ 8
qs= xs.^3 .+ 3xs.^2 .- 4xs .-12
ys= ps ./ qs
plt.plot(xs, ys)
plt.ylim(-10,10)
plt.xlim(-3,3)
plt.axhline(0, color="k", lw=0.5)
plt.axvline(-3, color="k", lw=0.5)
plt.axvline(-2, color="k", lw=0.5)
plt.axvline(2, color="k", lw=0.5)

▲ 練習

上の有理関数で、$x=-2$ に対する値を求めよ。

分子・分母は共通項 $(x+2)$ で割った関数のグラフを描き、 上のグラフと重なることを確かめよ。二つの曲線を比較するための描き方は、下の ▼ 周期関数 を参考にせよ(本章を通読してから取り組め)。

▼ 正接関数・余接関数を描く

  • 正接 $y = \tan{x} =\dfrac{\sin{x}}{\cos{x}}$
  • 余接 $y = \cot{x} =\dfrac{\cos{x}}{\sin{x}}$

ラジアン単位

正接 $\tan{x}$は、$\dfrac{\pi}{2}$ の奇数倍で不連続である。

余接 $\cot{x}$は、$\dfrac{\pi}{2}$ の偶数倍で不連続である。

using PyPlot
xs=-2pi:pi/360:2pi
plt.plot(xs, tan.(xs), label="tan")
plt.plot(xs, cot.(xs), label="cot")
plt.ylim(-1e1, 1e1)
plt.xlabel("radian")
plt.legend()

角度単位

using PyPlot
xs=-360:1:360
plt.plot(xs, tand.(xs), label="tand")
plt.plot(xs, cotd.(xs), label="cotd")
plt.xlabel("degree")
plt.ylim(-1e1, 1e1)
plt.legend()

▼ 周期関数

\[f(t+T) = f(t)\]

上式のように、横軸を $T$ だけ平行移動しても、 元の形に重なる関数を周期関数 (periodic function)という。 $T$ は、周期 (period) と呼ばれる。

●▼ 周期関数を確認する

ラジアン単位の正接関数 tan は、周期 $2\pi$である。 平行移動して重なることを、図示してみよう。

比較の基準となる曲線は fmt="bo" (blue, circle, 青い円) で描いた。

比較される曲線は fmt="r." (red, point, 赤い点) で描いた。

青い円の真ん中に、赤い点が描かれ、同じ位置に描かれることが分かる。

using PyPlot
xs=-2pi:pi/18:2pi
plt.plot(xs, tan.(xs        ), "bo", label="tan")
plt.plot(xs, tan.(xs .+ 2*pi), "r.", label="tan, shifted by 2pi")
plt.ylim(-1e1, 1e1)
plt.xlim(-1.2*pi, 1.2*pi)
plt.xlabel("radian")
plt.legend()

▼ 符号関数を描く

Base.sign - Function

関数 sign(x) は、

  • \[x > 0\]
    なら $1$ を、
  • \[x = 0\]
    なら $0$ を、
  • \[x < 0\]
    なら $-1$ を、

それぞれ返す。

using PyPlot
xs=-6.4:0.1:6.4
plt.plot(xs, sign.(xs), ".")

三角関数と関数 sign とを組み合わると、 不連続な周期関数を作ることができる。

▶ 方形波を描く

二つの一定値を交互にとる周期関数を方形波 (square wave)という。

plt.plot(xs, cos.(xs), "r", label="cos(x)")
plt.plot(xs, sign.( cos.(xs)), "b.", label="sign(cos(x))")
plt.legend()

▲ 練習

  • 上の例の周期はいくつか?
  • 周期が 1 になるように、変更してみよ。グラフを描け。

▼ 絶対値関数

関数 abs(x)は、$x$の絶対値を返す。

using PyPlot
plt.axes().set_aspect("equal")
xs=-1:0.1:1
plt.plot(xs,abs.(xs))

絶対値関数の符号を変えたり、平行移動すると、色々な山や谷の形を描くことができる。

using PyPlot
plt.axes().set_aspect("equal")
xs=-2pi:pi/18:2pi
# 符号を変える。山の形
plt.plot(xs, -abs.(xs), label="-abs(x)")
# 縦軸の平行移動
plt.plot(xs, pi .- abs.(xs), label="pi-abs(x)")
# さらに、横軸の平行移動
plt.plot(xs, pi .- abs.(xs .- pi), label="pi-abs(x-pi)")
plt.legend()
plt.xlabel("x")
plt.axhline(0,color="k",lw=0.5)
plt.axvline(0,color="k",lw=0.5)
plt.axvline(pi,color="k",lw=0.5)

▼ クランプ関数

Base.Math.clamp

関数 clamp(x, lo, hi) は、上限と下限で制限する関数である。 すなわち、$x$ の値が hi よりも大きければ hiを、lo よりも大きければ loを返す。 どちらでもなければ、そのままの値を返す。

using PyPlot
plt.axes().set_aspect("equal")
xs=-5:0.1:5
plt.plot(xs,clamp.(xs,-1,2))
plt.xlim(-5,5)
plt.ylim(-5,5)

■ 床関数・天井関数

床関数 floor(x) は、$x$ 以下の最大の整数を返す。

天井関数 ceil(x) は、$x$ 以上の最小の整数を返す。

下のグラフで、整数 $x$ に対する関数の値を、よく観察せよ。

これらの関数は、■ 浮動小数点数から整数への変換 で用いられる。

using PyPlot
plt.axes().set_aspect("equal")
xs=-2.4:0.2:2.4
plt.plot(xs, ceil.(xs), "o", label="ceil")
plt.plot(xs, floor.(xs), ".", label="floor")
for x in -2:2
  plt.axvline(x, color="k", lw=0.5)
  plt.axhline(x, color="k", lw=0.5)
end
plt.xlim(-3.2,3.2)
plt.ylim(-3.2,3.2)

plt.legend()

▲ 練習

床関数または天井関数を用いて、 正の数を 1の位で四捨五入するには、どうしたらよいか?

1の位での四捨五入とは、その数の小数点第一桁目が 5以上であれば 元の数に 1を加え、5未満であれば何もしない操作である。

プログラムを書いて、グラフを描き、確認してみよ。 特に、小数点以下が 0.5 に等しい場合の結果を観察せよ。

Note

数字のおおよその値を表すのに、四捨五入がよく用いられるが、科学技術分野で単純な四捨五入は適当ではない。「数字の丸め方」は、国際規格 ISO 31-0 : 1992 に相当する日本工業規格 JIS Z8401 : 1999 に定められている。JIS規格の全文は、例えば、ここで読める。→ kikakurui Z8401-1999-01

▲ 練習

ここまで紹介した関数を使って、色々な不連続曲線や周期関数を描いてみよ。 Jupyter notebookの Markdownセルを用いて、説明文も加えよ。

★ 今回のまとめ

  • plot 関数のフォーマットパラメータ
  • 0 による除算
  • 逆数関数
  • 不連続な有理関数
  • 正接・余接関数
  • 周期関数
  • 符号関数
  • 絶対値関数
  • 床関数・天井関数