質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Matplotlib

MatplotlibはPythonのおよび、NumPy用のグラフ描画ライブラリです。多くの場合、IPythonと連携して使われます。

NumPy

NumPyはPythonのプログラミング言語の科学的と数学的なコンピューティングに関する拡張モジュールです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

2回答

9673閲覧

Pythonで、複数の座標情報から、その座標を通る三角関数や指数・対数関数の式あるいは近似式を導出したい

tukejonnyBot

総合スコア14

Matplotlib

MatplotlibはPythonのおよび、NumPy用のグラフ描画ライブラリです。多くの場合、IPythonと連携して使われます。

NumPy

NumPyはPythonのプログラミング言語の科学的と数学的なコンピューティングに関する拡張モジュールです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

1グッド

3クリップ

投稿2015/07/26 04:21

編集2015/07/26 05:12

数学寄りの質問で大変申し訳ないのですが、
Pythonで、複数の座標情報(座標情報は、いくつでも取得できることを想定。もちろん、利用する座標情報はなるべく少ない方が良い)を元に、その座標を通る三角関数や指数・対数関数の式あるいは近似式を導出したいと考えております(その式の係数を求めることになります)。なお、三角関数、指数・対数関数のどの関数の式であるかがわかっている前提とします。

今のところ、うまく導き出す方法を考えられておらず、
・座標を用いて計算を行い、導き出す
・Pythonで利用出来る関数に、導出してくれる関数があり、それを用いることで導き出す
・wolframのようなサイトがあって、そこのAPIに導出してくれる関数があり、それを用いることで導き出す
・例えば正弦波なら、y = asin(bx) + cの式の、a, b, cのとりうる範囲を限定し、二分探索などで、座標が一致しているかチェックすることで導き出す
という4つのぼんやりした方法しか思いつきません。

ネット上で関連した記事を探してみたのですが、Excelのソルバーや物理学(正弦波、余弦波、正接波など)などの記事しか見つかりませんでした。

なにか他に良い、式の導出(式の係数を求める)方法はありませんでしょうか?
プログラム関連のQ&Aサイトにこういった質問を投稿するのはお門違いな気もするのですが、どなたかご教授頂けないでしょうか?

shunseki👍を押しています

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

swordone

2015/07/26 04:46

与えられた座標を通る(または近似する)三角関数なり指数・対数関数なりの係数を求めるという意味に見えるのですが,違うのですか?
tukejonnyBot

2015/07/26 05:01

はい。そうなります。 説明不足でした。申し訳ありません・・・
guest

回答2

0

最小二乗法が使いやすいと思います.
いくつか追加のモジュールが必要です.
Macで試したのですが,NumPyとMatplotLibとSciPyをインストールすれば良いと思います.

mash

1$ pip3 install numpy 2$ pip3 install matplotlib 3$ pip3 install scipy

その上で,以下のコードを実行してみてください.
テストに使ったデータは y = x ** 2 + 1 の座標です.
2次関数の一般形 y = a * x ** 2 + b * x + c を定義して,
そのパラメータを推定しています.
a_fit,b_fit,c_fitにそれぞれ推定したパラメータが格納されます.
三角関数,指数・対数関数などでも利用できると思うので,試してみてください.

python

1import numpy as np 2import matplotlib.pyplot as plt 3from scipy import optimize 4 5x = np.array([0, 1, 2, 3, 4, 5, 6, 7]) 6y = np.array([1, 2, 5, 10, 17, 26, 37, 50]) 7 8def fit_func(parameter,x,y): 9 a = parameter[0] 10 b = parameter[1] 11 c = parameter[2] 12 residual = y-(a*x**2+b*x+c) 13 return residual 14 15parameter0 = [0.,0.,0.] 16result = optimize.leastsq(fit_func,parameter0,args=(x,y)) 17a_fit=result[0][0] 18b_fit=result[0][1] 19c_fit=result[0][2] 20print(a_fit,b_fit,c_fit) 21 22#PLot 23plt.figure(figsize=(8,5)) 24plt.plot(x,y,'bo', label='Exp.') 25plt.plot(x,a_fit*x**2+b_fit*x+c_fit,'k-', label='fitted parabora', linewidth=10, alpha=0.3) 26plt.xlabel('X-axis') 27plt.ylabel('Y-axis') 28plt.legend(loc='best',fancybox=True, shadow=True) 29plt.grid(True) 30plt.show()

参考
フィッティング3(最小二乗法,optimizeの利用) — Mechanical Design Lab. of TUMSAT 1.0 documentation

投稿2015/07/26 11:02

編集2015/07/26 11:25
KenTerada

総合スコア751

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

tukejonnyBot

2015/07/26 14:18

回答ありがとうございます!! 最小二乗法という方法があるのですね・・・ 勉強不足で大変申し訳ないのですが、一つわからないところがあります。 optimize.leastsq()の返り値が二次元配列になっているのですが、値はどのように格納されているのでしょうか? 単純にパラメータ1つ目からresult[0][1], result[0][2], ..., result[1][0], result[1][1],...となっているのでしょうか? 実際に三角関数(sin)のグラフを描画してみました。描画されているグラフはあっていそうなのですが、パラメータが少しおかしいように思えます ```Python import numpy as np import matplotlib.pyplot as plt from scipy import optimize from math import* """ test data """ x = np.array([r for r in range(1, 1000)]) y = np.array([sin(pi * (r) / 180.0) for r in range(1, 1000)]) """ test data """ def calcSin(angle): rad = pi * angle / 180.0 for r in range(0, len(angle)): angle[r] = sin(rad[r]) return(angle) def fit_func(parameter, x, y): a = parameter[0] b = parameter[1] c = parameter[2] residual = y-(a*calcSin(b * x)+c) return(residual) parameter0 = [0.,0.,0.] result = optimize.leastsq(fit_func, parameter0, args=(x, y)) print "result is " + str(result) a_fit = result[0][0] b_fit = result[0][1] c_fit = result[0][2] print "y = (" + str(a_fit) + ")sin((" + str(b_fit) + ")x) + " + str(c_fit) #PLot plt.figure(figsize=(8,5)) plt.plot(x,y,'bo', label='Exp.') plt.plot(x,a_fit*calcSin(b_fit * x)+c_fit,'k-', label='fitted parabora', linewidth=10, alpha=0.3) plt.xlabel('X-axis') plt.ylabel('Y-axis') plt.legend(loc='best',fancybox=True, shadow=True) plt.grid(True) plt.show() ``` 出力結果(グラフは除く) y = (0.0)sin((0.0)x) + 0.0478855562909 これだとxの値に関わらず、yが0.0478855562909となるように見えてしまいます。 出力結果として、これは正しいのでしょうか?
KenTerada

2015/07/26 16:24

scipy.optimize.leastsqの返り値がresultだったとき, これは2次元配列になっていて, result[0]が推定パラメータ,result[1]がパラメータの誤差だそうです. result[0]ばかり気にしていたので,result[1]が真に何を意味するのかはわかりません.
guest

0

コメントだとコードが見にくくなるので,別の所へ.
確かに,色々やってみましたが上手く行きませんでした.
入力データを変えた所上手く動いたのですが,なぜだかわからずじまいです.
もしかしたらどこかで,浮動小数の情報落ち,桁落ちなどで
値の更新がされなくなってしまったのかもしれません.
(最小二乗法は,計算を何度も繰り返して最小になる値を求めるので)

pylabのsin関数は配列に対しても行えると聞いたので,使っています.
よくよく考えたら,yの式をmyfitか何かで宣言しておいて,
mydiffか何かで入力データとの差を取れば良いかなと思いました.

また,初期値も[0.,0.,0.]でやるとエラーになることを確認しています.
最小二乗法では最小値を推定する計算があるのですが,
その方法を使う時にいくつか制限があるということです.
この場合は1番目の値が0だとだめなようです.
(ヤコビ行列が陽,と私にもさっぱりの定義でした)

python

1import matplotlib.pyplot as plt 2from scipy import optimize 3from math import * 4import pylab 5 6""" test data """ 7x = [(pi * (r) / 180.0) for r in range(1, 1000)] 8y = pylab.sin(x) 9""" test data """ 10 11def myfit(p, x): 12 return(p[0]*pylab.sin(p[1]*x)+p[2]) 13 14def mydiff(p, x, y): 15 return(y-myfit(p,x)) 16 17p0 = [1.0,1.0,1.0] 18result = optimize.leastsq(mydiff, p0, args=(x,y)) 19pr = result[0] 20print pr 21 22#Plot 23plt.figure(figsize=(8,5)) 24plt.plot(x,y,'bo', label='Exp.') 25plt.plot(x,myfit(pr,x),'k-', label='fitted curb', linewidth=10, alpha=0.3) 26plt.xlabel('X-axis') 27plt.ylabel('Y-axis') 28plt.legend(loc='best',fancybox=True, shadow=True) 29plt.grid(True) 30plt.show()

投稿2015/07/26 16:12

編集2015/07/26 16:25
KenTerada

総合スコア751

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問