Python for .NETの新しい話
だいぶん前に「PythonからC#で書いた.NET Framewokのクラスライブラリを読みだす」1つ目,2つ目
では.NET Frameworkのプログラムを読み出すことだった。
逆の「C#からPythonの関数を呼び出し」は更新が追い付いていないといって最新版をとってきていた。
多少最新バージョンからバージョンがずれていてもよいならpythonnet_py37_winなどなどnugetで入れられるようになっていた。むしろこちらの方が簡単だな。
nugetパッケージは.NET Frameworkならpythonnet_py37_winだし.NET Coreならpythonnet_netstandard_py37_win
やっぱりnugetパッケージは簡単.ただし,embeddable pythonをビルドターゲットフォルダに持ってきている。この参考でscipyまたはnumpyをインストールした方が便利。
ターゲットに入れて一緒に持ち運び....(scipyまで入れると相当 大きい)
using Python.Runtime; using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Reflection; using System.Text; using System.Threading.Tasks; namespace PythonEmbedSample { class Program { static void Main(string[] args) { string strPath = Environment.GetEnvironmentVariable("PATH"); string appDir = Directory.GetParent(Assembly.GetExecutingAssembly().Location).FullName + @"\python"; Environment.SetEnvironmentVariable("PATH", Path.PathSeparator + appDir, EnvironmentVariableTarget.Process); using (Py.GIL()) { PythonEngine.RunSimpleString("print('SAMPLE')"); } } } }
python37._pthの#import siteのコメントアウトを解除して,https://bootstrap.pypa.io/get-pip.pyをもらってきて,...
embeddable pythonのディレクトリでpython get-pip.pyを実行して,
python -m pip install scipyを実行して... scipyを使えるようになった
例えば,sample.pyを作る splineで補間する例を追加してみた.
import numpy as np from scipy import interpolate def spline(x, y, xi): x = np.array(x); y = np.array(y); xi = np.array(xi); f = interpolate.interp1d(x, y, kind="cubic", fill_value="extrapolate") yi = f(xi); return yi;
そしてC#の側を次のようにいじってsample.pyのモジュールを読み込むようにする.
using Python.Runtime; using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Reflection; using System.Text; using System.Threading.Tasks; namespace PythonEmbedSample { class Program { static void Main(string[] args) { string strPath = Environment.GetEnvironmentVariable("PATH"); string appDir = Directory.GetParent(Assembly.GetExecutingAssembly().Location).FullName + @"\python"; Environment.SetEnvironmentVariable("PATH", Path.PathSeparator + appDir, EnvironmentVariableTarget.Process); using (Py.GIL()) { dynamic sys = Py.Import("sys"); // sample.pyを置くフォルダをパスに追加 sys.path.append(Directory.GetParent(Assembly.GetExecutingAssembly().Location).FullName); dynamic sample = Py.Import("sample"); List<double> x = new List<double>(); // Python listへの変換予定 List<double> y = new List<double>(); // Python listへの変換予定 for (int i = 0; i < 10; i++) { x.Add(0.1 * i); y.Add(Math.Sin(2.0 * Math.PI * x[i] / 1.0)); } List<double> xi = new List<double>(); // Python listへの変換予定 for (int i = 0; i < 100; i++) { xi.Add(0.01 * i); } dynamic yi_ = sample.spline(x, y, xi); // numpy.arrayで返ってくる予定 List<double> yi = new List<double>(); // List<double>への変換は暗黙的にできないため yi.AddRange((double[])yi_); { StreamWriter sw = new StreamWriter("sample_init.csv"); for (int i = 0; i < x.Count; i++) { sw.WriteLine(string.Format("{0},{1}", x[i], y[i])); } sw.Close(); } { StreamWriter sw = new StreamWriter("sample_interp.csv"); for (int i = 0; i < xi.Count; i++) { sw.WriteLine(string.Format("{0},{1}", xi[i], yi[i])); } sw.Close(); } } } } }
タグ:Python