はじめに
iRubyでデータ分析をすることが増えてきたので、グラフを描画できないことにより致命的に困っています。
これまでPython(jupyter)でデータ分析を行ってきたことから、PyPlotのようなライブラリがあればいいなと思ったので、同じことができるようにクラスを作ってみました。
PyPlotでは
以下のような方法でグラフが描画できます。
import matplotlib.pyplot as plt
plt.plot([4,6,5,7,8,1])
plt.show()
なので、同じようにするならこんな感じでできないかなと...
require 'rbplot'
plt = RbPlot.new()
plt.plot([4,6,5,7,8,1])
plt.show()
RbPlotというクラスを作ってみる
先日、gnuplotを使えばiRubyの中でグラフを表示できるようになるということがわかったので、これを利用することにします。
必要最低限のものを作ってみると以下のとおり。
class RbPlot
def initialize()
@data = []
end
def plot(data)
@data = data
end
def show()
IRuby.display make(), mime: 'image/svg+xml'
end
def make()
Gnuplot.open do |gp|
Gnuplot::Plot.new( gp ) do |myplot|
myplot.terminal "svg"
myplot.data << Gnuplot::DataSet.new(@data) do |ds|
ds.with = "lines"
ds.notitle
end
end
end
end
end
使い方は以下のとおり。
plt = RbPlot.new
plt.plot([4,6,5,7,8,1])
plt.show()
できた!
二本の線を描くには
PyPlotでは、以下のように記述すると描画できます。
import matplotlib.pyplot as plt
plt.plot([4,6,5,7,8,1])
plt.plot([2,4,3,6,5,9])
plt.show()
...これは便利だ(-_-;)
では、同じようにできるよう先ほどのクラスを改造してみます。
class RbPlot2
def initialize()
@datas = []
end
def plot(data)
@datas << data
end
def show()
IRuby.display make(), mime: 'image/svg+xml'
end
def make()
Gnuplot.open do |gp|
Gnuplot::Plot.new( gp ) do |myplot|
myplot.terminal "svg"
@datas.each do |data|
myplot.data << Gnuplot::DataSet.new(data) do |ds|
ds.with = "lines"
ds.notitle
end
end
end
end
end
end
できた!
グラフのタイトルを追加
PyPlotでタイトルを表示しようとすると以下のとおりです。
import matplotlib.pyplot as plt
plt.title("PyPlot")
plt.plot([4,6,5,7,8,1])
plt.plot([2,4,3,6,5,9])
plt.show()
これもできるようにしてみます。
class RbPlot
def initialize()
@datas = []
@title = ""
end
def title(title)
@title = title
end
def plot(data)
@datas << data
end
def show()
IRuby.display make(), mime: 'image/svg+xml'
end
def make()
Gnuplot.open do |gp|
Gnuplot::Plot.new( gp ) do |myplot|
myplot.terminal "svg"
myplot.title @title
@datas.each do |data|
myplot.data << Gnuplot::DataSet.new(data) do |ds|
ds.with = "lines"
ds.notitle
end
end
end
end
end
end
できた!
最終的に...
その後もごにょごにょいじっていたら、それなりにできた!
require 'gnuplot'
class RbPlot
def initialize()
@arbitrary_lines = []
@arbitrary_lines << "set terminal svg"
@datas = []
end
def title(title)
@arbitrary_lines << "set title '#{title}'"
end
def xlabel(xlabel)
@arbitrary_lines << "set xlabel '#{xlabel}'"
end
def ylabel(ylabel)
@arbitrary_lines << "set ylabel '#{ylabel}'"
end
def xlim(min, max)
@arbitrary_lines << "set xrange [#{min}:#{max}]"
end
def ylim(min, max)
@arbitrary_lines << "set yrange [#{min}:#{max}]"
end
def arbitrary_lines(value)
@arbitrary_lines << "set " + value
end
def plot(value)
@datas << {
"type" => "lines",
"value" => value
}
end
def scatter(value)
@datas << {
"type" => "circles",
"value" => value
}
end
def show()
IRuby.display make(), mime: 'image/svg+xml'
end
def make()
Gnuplot.open do |gp|
Gnuplot::Plot.new( gp ) do |myplot|
@arbitrary_lines.each do |value|
myplot.arbitrary_lines << value
end
@datas.each do |data|
@with = data["type"]
myplot.data << Gnuplot::DataSet.new(data["value"]) do |ds|
ds.with = @with
ds.notitle
end
end
end
end
end
end
plt = RbPlot.new
x = [ 1, 3, 9]
y = [10,-2,-5]
plt.title("RbPlotテスト")
plt.ylabel("Y")
plt.xlabel("エックス")
plt.xlim(0,10)
plt.ylim(-10,20)
plt.arbitrary_lines("grid")
plt.plot([4,6,5,7,8,1])
plt.plot([2,4,3,6,5,9])
plt.plot([x,y])
plt.plot("x * x / 10")
plt.plot("10 * sin(x / 5 * 3.14)")
plt.show()
どう?(^-^)
これで、それなりにiRubyでグラフが使えるようになった気がします。