裏 RjpWiki

Julia ときどき R, Python によるコンピュータプログラム,コンピュータ・サイエンス,統計学

Julia に翻訳--025 プロット関数群

2021年03月05日 | ブログラミング

#==========
Julia の修行をするときに,いろいろなプログラムを書き換えるのは有効な方法だ。
以下のプログラムを Julia に翻訳してみる。

プロット関数群
http://aoki2.si.gunma-u.ac.jp/R/plot.html

ファイル名: plotter.jl  関数名: plot*

翻訳するときに書いたメモ

なかなか楽しかった。色々拡張した。
前に NHK でやっていた,家紋を描くシリーズを見ていたので,ちょっとやってみた。

==========#

using Plots

# 開始
function plotbegin(; w = 600, h = 600)
    pyplot()
    plt = plot(xlabel="", ylabel="", grid=false, showaxis=false,
               aspect_ratio=1, size=(w, h), label="")
end

# 終了
function plotend()
    plot!()
end

# (x1, y1) - (x2, y2) の線分
function plotline(x1, y1, x2, y2; col=:black, lty=:solid, lwd=1)
    plot!([x1, x2], [y1, y2], linecolor=col, linestyle=lty, linewidth=lwd, label="")
end

# (x1, y) - (x2, y) の水平線分
function plothline(x1, x2, y; col=:black, lty=:solid, lwd=1)
    plot!([x1, x2], [y, y], linecolor=col, linestyle=lty, linewidth=lwd, label="")
end

# (x, y1) - (x, y2) の垂直線分
function plotvline(x, y1, y2; col=:black, lty=:solid, lwd=1)
    plot!([x, x], [y1, y2], linecolor=col, linestyle=lty, linewidth=lwd, label="")
end

# (x1, y1), (x2, y2) を対角座標とする矩形
function plotbox(x1, y1, x2, y2; col=:black, lty=:solid, lwd=1, fcol="")
    if fcol == ""
        plot!([x1, x2, x2, x1, x1], [y1, y1, y2, y2, y1], linecolor=col,
              linestyle=lty, linewidth=lwd, label="")
    else
        plot!([x1, x2, x2, x1, x1], [y1, y1, y2, y2, y1], linecolor=col,
              linestyle=lty, seriestype=:shape, linewidth=lwd, fillcolor=fcol,
              label="")
    end
end

# (ox, oy) を原点とする半径 r の円(円弧)。fcol を指定すると塗りつぶし。
function plotcircle(ox, oy, r; startangle=0, endangle=360,
                    col=:black, lty=:solid, lwd=1, fcol="")
    plotellipse(ox, oy, r, r, φ=0, startangle=startangle,
                endangle=endangle, col=col, lty=lty, lwd=lwd, fcol=fcol)
end

# 度をラジアンに変換する
radian(degree) = degree / 180 * π

# (ox, oy) を中心,ra, rb を半径とする楕円(楕円弧)。fcol を指定すると塗りつぶし。
function plotellipse(ox, oy, ra, rb; φ=0, startangle=0, endangle=360,
                     length=100, col=:black, lty=:solid, lwd=1, fcol="")
    θ = vcat(range(radian(startangle), radian(endangle),
              length=length), radian(endangle))
    if φ == 0
        if fcol == ""
            plot!(ra .* cos.(θ) .+ ox, rb .* sin.(θ) .+ oy,
                  linecolor=col, linestyle=lty, linewidth=lwd, label="")
        else
            plot!(ra .* cos.(θ) .+ ox, rb .* sin.(θ) .+ oy,
                  linecolor=col, linestyle=lty, linewidth=lwd,
                  seriestype=:shape, fillcolor=fcol, label="")
        end
    else
        x = ra .* cos.(θ)
        y = rb .* sin.(θ)
        φ = radian(φ)
        cosine = cos(φ)
        sine = sin(φ)
        if fcol == ""
            plot!(cosine .* x .- sine .* y .+ ox,
                  sine .* x .+ cosine .* y .+ oy,
                  linecolor=col, linestyle=lty, linewidth=lwd, label="")
        else
            plot!(cosine .* x .- sine .* y .+ ox,
                  sine .* x .+ cosine .* y .+ oy,
                  linecolor=col, linestyle=lty, linewidth=lwd,
                  seriestype=:shape, fillcolor=fcol, label="")
        end
    end
end

# 任意の多角形。fcol を指定すると塗りつぶし。
function plotpolygon(x, y; col=:black, lty=:solid, lwd=1, fcol="")
    x = vcat(x, x[1])
    y = vcat(y, y[1])
    if fcol == ""
        plot!(x, y, linecolor=col, linestyle=lty, linewidth=lwd, label="")
    else
        plot!(x, y, linecolor=col, linestyle=lty, linewidth=lwd,
              seriestype=:shape, fillcolor=fcol, label="")
    end
end

# (x1, y1) を描き始め,一辺の長さ l の正 n 多角形。fcol を指定すると塗りつぶし。
function plotpolygon1(x1, y1, l, n; col=:black, lty=:solid, lwd=1, fcol="")
    θ = range(0, 2π, length=n+1)
    x = fill(float(x1), n+1)
    y = fill(float(y1), n+1)
    for i = 2:n
        x[i] = x[i-1]+l*cos(θ[i])
        y[i] = y[i-1]+l*sin(θ[i])
    end
    if fcol == ""
        plot!(x, y, linecolor=col, linestyle=lty, linewidth=lwd, label="")
    else
        plot!(x, y, linecolor=col, linestyle=lty,
              seriestype=:shape, fillcolor=fcol, linewidth=lwd, label="")
    end
end

# (ox, oy) を中心,r を半径とする円に内接する正 n 多角形。fcol を指定すると塗りつぶし。
function plotpolygon2(ox, oy, r, n; φ=90, col=:black, lty=:solid, lwd=1, fcol="")
    θ = range(0, 2π, length=n+1) .+ radian(φ)
    if fcol == ""
        plot!(r .* cos.(θ) .+ ox, r .* sin.(θ) .+ oy,
              linecolor=col, linestyle=lty, linewidth=lwd, label="")
    else
        plot!(r .* cos.(θ) .+ ox, r .* sin.(θ) .+ oy,
              linecolor=col, linestyle=lty, linewidth=lwd,
              seriestype=:shape, fillcolor=fcol, label="")
    end
end

# (x1,y1) - (x2, y2) の矩形範囲に格子を描く。間隔は wx, wy。
function plotgrid(x1, y1, x2, y2, wx; wy=wx, col=:gray, lty=:dot, lwd=1)
    X1 = min(x1, x2)
    X2 = max(x1, x2)
    Y1 = min(y1, y2)
    Y2 = max(y1, y2)
    for i = 0:fld(abs(X2-X1), wx)
        plot!([X1+wx*i, X1+wx*i], [Y1, Y2], linecolor=col,
              linestyle=lty, linewidth=lwd, label="")
    end
    for i = 0:fld(abs(y2-y1), wy)
        plot!([X1, X2], [Y1+wy*i, Y1+wy*i], linecolor=col,
              linestyle=lty, linewidth=lwd, label="")
    end
end

# ネフロイド
plotbegin()
t = 0:3:360
l = 130
ox = l .* cos.(radian.(t))
oy = l .* sin.(radian.(t))
for i = 1:length(t)
    plotcircle(ox[i]+250, oy[i]+250, abs(ox[i]),
               startangle=0, endangle=360, col="blue")
end
plotend()

# カージオイド
plotbegin()
t = 0:5:360
l = 100
ox = l .* cos.(radian.(t))
oy = l .* sin.(radian.(t))
for i = 1:length(t)
    plotcircle(ox[i]+320, oy[i]+250,
               sqrt((ox[i]-ox[1])^2+(oy[i]-oy[1])^2),
               startangle=0, endangle=360, col="blue")
end
plotend()

# 多角形1
using FixedPointNumbers, ColorTypes # for RGB
plotbegin();
for i = 30:-1:3
    plotpolygon1(0, 0, 70, i, fcol=RGB((70-i)/70, 0, 0))
end
plotend()

# 多角形2
plotbegin();
for i = 30:-1:3
    plotpolygon2(0, 0, 70, i, fcol=RGB(0, (30-i)/30, 0))
end
plotend()

plotbegin(h=300)
plotpolygon2(0, 0, 90, 3, φ = 90, fcol=:black)
plotpolygon2(0, 0, 90, 3, φ = 30, fcol=:black)
for θ = 0:30:330
    plotline(0, 0, 100*cos(radian(θ)), 100*sin(radian(θ)), col=:white, lwd=2)
end
newx = 200
plotcircle(newx, 0, 90, fcol=:black)
plotcircle(newx, 0, 82, fcol=:white)
plotpolygon2(newx, 0, 78, 3, φ = 90, fcol=:black)
plotpolygon2(newx, 0, 78, 3, φ = 30, fcol=:black)
for θ = 0:30:330
    plotline(newx, 0, newx+81*cos(radian(θ)), 81*sin(radian(θ)), col=:white, lwd=2)
end
plotend()

コメント    この記事についてブログを書く
  • X
  • Facebookでシェアする
  • はてなブックマークに追加する
  • LINEでシェアする
« Julia に翻訳--024 連関比率法 | トップ | Julia に翻訳--026 多項分布 »
最新の画像もっと見る

コメントを投稿

ブログラミング」カテゴリの最新記事