├── .gitattributes
├── .gitignore
├── README.md
├── SimpleDataPrediction.sln
└── SimpleDataPrediction
├── App.config
├── Datas.cs
├── Forecaster.cs
├── GaussNewton.cs
├── MyMatrix.cs
├── Program.cs
├── Properties
└── AssemblyInfo.cs
├── SimpleDataPrediction.csproj
├── SquareMatrix.cs
├── data.txt
└── packages.config
/.gitattributes:
--------------------------------------------------------------------------------
1 | ###############################################################################
2 | # Set default behavior to automatically normalize line endings.
3 | ###############################################################################
4 | * text=auto
5 |
6 | ###############################################################################
7 | # Set default behavior for command prompt diff.
8 | #
9 | # This is need for earlier builds of msysgit that does not have it on by
10 | # default for csharp files.
11 | # Note: This is only used by command line
12 | ###############################################################################
13 | #*.cs diff=csharp
14 |
15 | ###############################################################################
16 | # Set the merge driver for project and solution files
17 | #
18 | # Merging from the command prompt will add diff markers to the files if there
19 | # are conflicts (Merging from VS is not affected by the settings below, in VS
20 | # the diff markers are never inserted). Diff markers may cause the following
21 | # file extensions to fail to load in VS. An alternative would be to treat
22 | # these files as binary and thus will always conflict and require user
23 | # intervention with every merge. To do so, just uncomment the entries below
24 | ###############################################################################
25 | #*.sln merge=binary
26 | #*.csproj merge=binary
27 | #*.vbproj merge=binary
28 | #*.vcxproj merge=binary
29 | #*.vcproj merge=binary
30 | #*.dbproj merge=binary
31 | #*.fsproj merge=binary
32 | #*.lsproj merge=binary
33 | #*.wixproj merge=binary
34 | #*.modelproj merge=binary
35 | #*.sqlproj merge=binary
36 | #*.wwaproj merge=binary
37 |
38 | ###############################################################################
39 | # behavior for image files
40 | #
41 | # image files are treated as binary by default.
42 | ###############################################################################
43 | #*.jpg binary
44 | #*.png binary
45 | #*.gif binary
46 |
47 | ###############################################################################
48 | # diff behavior for common document formats
49 | #
50 | # Convert binary document formats to text before diffing them. This feature
51 | # is only available from the command line. Turn it on by uncommenting the
52 | # entries below.
53 | ###############################################################################
54 | #*.doc diff=astextplain
55 | #*.DOC diff=astextplain
56 | #*.docx diff=astextplain
57 | #*.DOCX diff=astextplain
58 | #*.dot diff=astextplain
59 | #*.DOT diff=astextplain
60 | #*.pdf diff=astextplain
61 | #*.PDF diff=astextplain
62 | #*.rtf diff=astextplain
63 | #*.RTF diff=astextplain
64 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | ## Ignore Visual Studio temporary files, build results, and
2 | ## files generated by popular Visual Studio add-ons.
3 | ##
4 | ## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
5 |
6 | # User-specific files
7 | *.rsuser
8 | *.suo
9 | *.user
10 | *.userosscache
11 | *.sln.docstates
12 |
13 | # User-specific files (MonoDevelop/Xamarin Studio)
14 | *.userprefs
15 |
16 | # Build results
17 | [Dd]ebug/
18 | [Dd]ebugPublic/
19 | [Rr]elease/
20 | [Rr]eleases/
21 | x64/
22 | x86/
23 | [Aa][Rr][Mm]/
24 | [Aa][Rr][Mm]64/
25 | bld/
26 | [Bb]in/
27 | [Oo]bj/
28 | [Ll]og/
29 |
30 | # Visual Studio 2015/2017 cache/options directory
31 | .vs/
32 | # Uncomment if you have tasks that create the project's static files in wwwroot
33 | #wwwroot/
34 |
35 | # Visual Studio 2017 auto generated files
36 | Generated\ Files/
37 |
38 | # MSTest test Results
39 | [Tt]est[Rr]esult*/
40 | [Bb]uild[Ll]og.*
41 |
42 | # NUNIT
43 | *.VisualState.xml
44 | TestResult.xml
45 |
46 | # Build Results of an ATL Project
47 | [Dd]ebugPS/
48 | [Rr]eleasePS/
49 | dlldata.c
50 |
51 | # Benchmark Results
52 | BenchmarkDotNet.Artifacts/
53 |
54 | # .NET Core
55 | project.lock.json
56 | project.fragment.lock.json
57 | artifacts/
58 |
59 | # StyleCop
60 | StyleCopReport.xml
61 |
62 | # Files built by Visual Studio
63 | *_i.c
64 | *_p.c
65 | *_h.h
66 | *.ilk
67 | *.meta
68 | *.obj
69 | *.iobj
70 | *.pch
71 | *.pdb
72 | *.ipdb
73 | *.pgc
74 | *.pgd
75 | *.rsp
76 | *.sbr
77 | *.tlb
78 | *.tli
79 | *.tlh
80 | *.tmp
81 | *.tmp_proj
82 | *_wpftmp.csproj
83 | *.log
84 | *.vspscc
85 | *.vssscc
86 | .builds
87 | *.pidb
88 | *.svclog
89 | *.scc
90 |
91 | # Chutzpah Test files
92 | _Chutzpah*
93 |
94 | # Visual C++ cache files
95 | ipch/
96 | *.aps
97 | *.ncb
98 | *.opendb
99 | *.opensdf
100 | *.sdf
101 | *.cachefile
102 | *.VC.db
103 | *.VC.VC.opendb
104 |
105 | # Visual Studio profiler
106 | *.psess
107 | *.vsp
108 | *.vspx
109 | *.sap
110 |
111 | # Visual Studio Trace Files
112 | *.e2e
113 |
114 | # TFS 2012 Local Workspace
115 | $tf/
116 |
117 | # Guidance Automation Toolkit
118 | *.gpState
119 |
120 | # ReSharper is a .NET coding add-in
121 | _ReSharper*/
122 | *.[Rr]e[Ss]harper
123 | *.DotSettings.user
124 |
125 | # JustCode is a .NET coding add-in
126 | .JustCode
127 |
128 | # TeamCity is a build add-in
129 | _TeamCity*
130 |
131 | # DotCover is a Code Coverage Tool
132 | *.dotCover
133 |
134 | # AxoCover is a Code Coverage Tool
135 | .axoCover/*
136 | !.axoCover/settings.json
137 |
138 | # Visual Studio code coverage results
139 | *.coverage
140 | *.coveragexml
141 |
142 | # NCrunch
143 | _NCrunch_*
144 | .*crunch*.local.xml
145 | nCrunchTemp_*
146 |
147 | # MightyMoose
148 | *.mm.*
149 | AutoTest.Net/
150 |
151 | # Web workbench (sass)
152 | .sass-cache/
153 |
154 | # Installshield output folder
155 | [Ee]xpress/
156 |
157 | # DocProject is a documentation generator add-in
158 | DocProject/buildhelp/
159 | DocProject/Help/*.HxT
160 | DocProject/Help/*.HxC
161 | DocProject/Help/*.hhc
162 | DocProject/Help/*.hhk
163 | DocProject/Help/*.hhp
164 | DocProject/Help/Html2
165 | DocProject/Help/html
166 |
167 | # Click-Once directory
168 | publish/
169 |
170 | # Publish Web Output
171 | *.[Pp]ublish.xml
172 | *.azurePubxml
173 | # Note: Comment the next line if you want to checkin your web deploy settings,
174 | # but database connection strings (with potential passwords) will be unencrypted
175 | *.pubxml
176 | *.publishproj
177 |
178 | # Microsoft Azure Web App publish settings. Comment the next line if you want to
179 | # checkin your Azure Web App publish settings, but sensitive information contained
180 | # in these scripts will be unencrypted
181 | PublishScripts/
182 |
183 | # NuGet Packages
184 | *.nupkg
185 | # The packages folder can be ignored because of Package Restore
186 | **/[Pp]ackages/*
187 | # except build/, which is used as an MSBuild target.
188 | !**/[Pp]ackages/build/
189 | # Uncomment if necessary however generally it will be regenerated when needed
190 | #!**/[Pp]ackages/repositories.config
191 | # NuGet v3's project.json files produces more ignorable files
192 | *.nuget.props
193 | *.nuget.targets
194 |
195 | # Microsoft Azure Build Output
196 | csx/
197 | *.build.csdef
198 |
199 | # Microsoft Azure Emulator
200 | ecf/
201 | rcf/
202 |
203 | # Windows Store app package directories and files
204 | AppPackages/
205 | BundleArtifacts/
206 | Package.StoreAssociation.xml
207 | _pkginfo.txt
208 | *.appx
209 |
210 | # Visual Studio cache files
211 | # files ending in .cache can be ignored
212 | *.[Cc]ache
213 | # but keep track of directories ending in .cache
214 | !?*.[Cc]ache/
215 |
216 | # Others
217 | ClientBin/
218 | ~$*
219 | *~
220 | *.dbmdl
221 | *.dbproj.schemaview
222 | *.jfm
223 | *.pfx
224 | *.publishsettings
225 | orleans.codegen.cs
226 |
227 | # Including strong name files can present a security risk
228 | # (https://github.com/github/gitignore/pull/2483#issue-259490424)
229 | #*.snk
230 |
231 | # Since there are multiple workflows, uncomment next line to ignore bower_components
232 | # (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
233 | #bower_components/
234 |
235 | # RIA/Silverlight projects
236 | Generated_Code/
237 |
238 | # Backup & report files from converting an old project file
239 | # to a newer Visual Studio version. Backup files are not needed,
240 | # because we have git ;-)
241 | _UpgradeReport_Files/
242 | Backup*/
243 | UpgradeLog*.XML
244 | UpgradeLog*.htm
245 | ServiceFabricBackup/
246 | *.rptproj.bak
247 |
248 | # SQL Server files
249 | *.mdf
250 | *.ldf
251 | *.ndf
252 |
253 | # Business Intelligence projects
254 | *.rdl.data
255 | *.bim.layout
256 | *.bim_*.settings
257 | *.rptproj.rsuser
258 | *- Backup*.rdl
259 |
260 | # Microsoft Fakes
261 | FakesAssemblies/
262 |
263 | # GhostDoc plugin setting file
264 | *.GhostDoc.xml
265 |
266 | # Node.js Tools for Visual Studio
267 | .ntvs_analysis.dat
268 | node_modules/
269 |
270 | # Visual Studio 6 build log
271 | *.plg
272 |
273 | # Visual Studio 6 workspace options file
274 | *.opt
275 |
276 | # Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
277 | *.vbw
278 |
279 | # Visual Studio LightSwitch build output
280 | **/*.HTMLClient/GeneratedArtifacts
281 | **/*.DesktopClient/GeneratedArtifacts
282 | **/*.DesktopClient/ModelManifest.xml
283 | **/*.Server/GeneratedArtifacts
284 | **/*.Server/ModelManifest.xml
285 | _Pvt_Extensions
286 |
287 | # Paket dependency manager
288 | .paket/paket.exe
289 | paket-files/
290 |
291 | # FAKE - F# Make
292 | .fake/
293 |
294 | # JetBrains Rider
295 | .idea/
296 | *.sln.iml
297 |
298 | # CodeRush personal settings
299 | .cr/personal
300 |
301 | # Python Tools for Visual Studio (PTVS)
302 | __pycache__/
303 | *.pyc
304 |
305 | # Cake - Uncomment if you are using it
306 | # tools/**
307 | # !tools/packages.config
308 |
309 | # Tabs Studio
310 | *.tss
311 |
312 | # Telerik's JustMock configuration file
313 | *.jmconfig
314 |
315 | # BizTalk build output
316 | *.btp.cs
317 | *.btm.cs
318 | *.odx.cs
319 | *.xsd.cs
320 |
321 | # OpenCover UI analysis results
322 | OpenCover/
323 |
324 | # Azure Stream Analytics local run output
325 | ASALocalRun/
326 |
327 | # MSBuild Binary and Structured Log
328 | *.binlog
329 |
330 | # NVidia Nsight GPU debugger configuration file
331 | *.nvuser
332 |
333 | # MFractors (Xamarin productivity tool) working folder
334 | .mfractor/
335 |
336 | # Local History for Visual Studio
337 | .localhistory/
338 |
339 | # BeatPulse healthcheck temp database
340 | healthchecksdb
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | 以前在工作中遇到了一个数据错误的问题,顺便写下解决的思路。
2 |
3 | ## 1. 错误的数据
4 |
5 | 
6 |
7 | 上图是同一组探测器在同一天采集到的 19 次数据,总体来说重复性不错,但很明显最后 8 个探测器出了问题,导致采集到的数据在最后八个点一片混乱。即使把其中看起来最好的一组数据拿出来使用多项式拟合,也可以看出最后几个点没有落在拟合曲线上(只拟合最后 14 个点):
8 |
9 | 
10 |
11 |
12 | 虽然我知道这是硬件问题,但是**遇到事情不能坐以待毙**,软件方面也许可以做些什么。既然我从上图中得知出了最后几个点之外,其它数据都在拟合曲线上,那我可以使用前面几个点的拟合结果预测后面几个点并替换掉出错的数据,从而得到一组看起来正常的数据。
13 |
14 |
15 | ## 2. 曲线拟合与数据预测
16 |
17 | 曲线拟合(curve fitting)是指选择适当的曲线类型来拟合观测数据,以便观察两组数据之间的内在联系,了解数据之间的变化趋势。
18 |
19 | 在数据分析时,我们有时需要通过已有数据来预测未来数据。在一些复杂的数据模型中,数据维度很多,数据之间的关系很复杂,我们可能会用到深度学习的算法。但是在一些简单的数据模型中,数据之间有很明显的相关性,那我们就可以使用简单的曲线拟合来预测未来的数据。
20 |
21 | 这些工作都可以使用 Excel 完成,先来尝试一下。把某组数据最后14个点(只选取峰值右边的14个点是因为容易计算)放进Excel中,插入一个散点图,右键点击其中的蓝色散点,选择`添加趋势线`:
22 |
23 | 
24 |
25 |
26 |
27 |
28 |
29 | 然后在右侧出现的`设置趋势线格式`中选择`多项式`,阶数为 3,勾选`显示公式`:
30 |
31 | 
32 |
33 |
34 |
35 | 可以看到,曲线图中出现了一条虚线的曲线,并显示了对应的公式为 y = 6E-07x^3^ + 0.0002x^2^ - 0.0072x + 0.0637
:
36 |
37 | 
38 |
39 | 如果需要预测数据,可以修改`前推`数字以得到后面几个周期的数据。
40 |
41 | ## 3. 使用 Math.Net 进行曲线拟合
42 |
43 | 当然我不可能对每一条数据都扔进 Excel 里进行拟合。在 C# 中我们可以使用 [Math.Net](https://www.mathdotnet.com/) 进行非线性拟合。
44 |
45 | [Math.Net](https://www.mathdotnet.com/) 是一个开源项目,旨在构建和维护涵盖基础数学的工具箱,以满足 .Net 开发人员的高级需求和日常需求。其中 [Math.NET Numerics](https://numerics.mathdotnet.com/) 旨在为科学、工程和日常使用中的数值计算提供方法和算法。涵盖的主题包括特殊函数,线性代数,概率模型,随机数,插值,积分变换等等。
46 |
47 | 要使用 [Math.NET Numerics](https://numerics.mathdotnet.com/),首先安装它的 Nuget 包:
48 |
49 | ```
50 | Install-Package MathNet.Numerics
51 | ```
52 |
53 | [Math.NET Numerics](https://numerics.mathdotnet.com/) 提供了 `Fit.Polynomial` 函数用作多项式拟合,如以下代码所示,其中 `X` 是 X 轴的数组, `Y` 是 Y 轴的数组, 函数的第三个参数是多项式的阶数,这里用 2 作为阶数。
54 |
55 | ``` CS
56 | double[] X = Enumerable.Range(1, 6).Select(r => (double)r).ToArray();
57 | double[] Y = values.ToArray();
58 | double[] parameters = Fit.Polynomial(X, Y, 2);
59 | ```
60 |
61 | 返回的结果是最佳拟合参数的数组 `[p0,p1,p2,…,pk]`,将其带入公式 p0 + p1×x + p2×x^2^ + ... + pk×x^k^
即可算出对应的拟合数据。完整的代码如下,在这个示例里,我只需要用倒数第9到14个数据,通过 `Fit.Polynomial` 获得一个多项式的方程 ( f(x) = p0 + p1×x + p2×x^2^
),然后用这个方程计算出后面 8 个点的数据替换原本出错的数据:
62 |
63 | ``` CS
64 | double[] X = Enumerable.Range(1, 6).Select(r => (double)r).ToArray();
65 | double[] Y = values.ToArray();
66 | double[] parameters = Fit.Polynomial(X, Y, 2);
67 |
68 |
69 | List result = new List();
70 | for (int i = 1; i < 15; i++)
71 | {
72 | result.Add(parameters[0] + parameters[1] * i + parameters[2] * i * i );
73 | }
74 |
75 | for (int i = 0; i < 8; i++)
76 | {
77 | data[data.Count - 1 - i] = result[result.Count - 1 - i];
78 | }
79 | ```
80 | 
81 |
82 |
83 |
84 |
85 | 替换后的结果如上所示,整体符合前面数据的趋势,使用这组数据进行运算也能得到很好的结果。
86 |
87 | ## 4. Microsoft Chart Controls 中的 FinancialFormula
88 |
89 | 接下来玩玩“新”花样,用古老的 Microsoft Chart Controls 实现相同的功能。
90 |
91 | 
92 |
93 |
94 |
95 |
96 | A long time ago in a galaxy far, far away... 微软推出了一套免费又强大的图表控件,它用于 WinForms 和 WebForms 中,可轻松套用各种功能强大的 2D、3D、实时变化的动态图表,头发比较少的 .NET 开发者或多或少都接触过这套图表控件。虽然现在看来多少有些落后了,但它还是很有用啊,而且还不收钱。
97 |
98 | 
99 |
100 | 那么,在哪里可以找到这个图表库呢?现在微软的官网也只能找到 for Microsoft .NET Framework 3.5 的[下载](https://www.microsoft.com/en-us/download/details.aspx?id=14422),找不到更新的版本。幸好 Visual Studio 里就自带了这个图表库,可以直接添加 `System.Windows.Forms.DataVisualization` 的引用:
101 |
102 | 
103 |
104 | 这篇我不会介绍如何做图表,而是讲讲这个图表库中的一样很有趣的东西:[FinancialFormula](https://docs.microsoft.com/zh-cn/dotnet/api/system.windows.forms.datavisualization.charting.dataformula.financialformula?view=netframework-4.8&WT.mc_id=WD-MVP-5003763)。如果只是做简单的财务数据处理,可以用它玩玩。当图表中已有其它序列(Series)的数据,DataManipulator 的 `FinancialFormula` 可以使用大部分常见的金融公式处理这些数据并产生新的数据序列。
105 |
106 | 例指,`数移动平均线 `(Exponential Moving Average) 是对一段时间内的数据计算所得的平均值,它的输入和输出如下:
107 |
108 | 
109 |
110 |
111 |
112 | 而`蔡金震荡` (Chaikin Oscillator) 指标是指应用于聚散的 3 天指数移动平均线与 10 天指数移动平均线之差,它的输出如下:
113 |
114 |
115 | 
116 |
117 |
118 |
119 |
120 | FinancialFormula 还有很多其它用法,具体可以参考以下两个页面:
121 |
122 | [FinancialFormula Enum (System.Windows.Forms.DataVisualization.Charting) Microsoft Docs](https://docs.microsoft.com/zh-cn/dotnet/api/system.windows.forms.datavisualization.charting.financialformula?view=netframework-4.8&WT.mc_id=WD-MVP-5003763)
123 |
124 | [Using Financial Formulas](https://origin2.cdn.componentsource.com/sites/default/files/resources/dundas/538236/WinChart2005/Formulas_HowToUseFormulas.html)
125 |
126 | ## 5. 数据预测
127 |
128 | 这次我用到的是`预测` (Forecasting) ,它是指使用历史观测值来预测未来值。
129 |
130 | 
131 |
132 |
133 |
134 | Forecasting公式采用四个可选参数:
135 |
136 |
137 | - **RegressionType**: 回归类型。使用一个数字来指示特定次数的多元回归,或者使用以下值之一指定不同的回归类型:Linear、Exponential、Logarithmic、Power。默认值为 2,与指定 Linear 等效。
138 |
139 | - **Period**: 预测时段。公式会预测此指定的未来天数内的数据变化。默认值为序列长度的一半。
140 |
141 | - **ApproxError**: 是否输出近似误差。如果设置为 false,则输出误差序列不包含相应历史数据的数据。默认值为 true。
142 |
143 | - **ForecastError**: 是否输出预测误差。如果设置为 false,并且 ApproxError 设置为 true,则输出误差序列将包含所有预测数据点的近似误差。默认值为 true。
144 |
145 | 输出值有三个序列:
146 |
147 | - **Forecast**: 预测测值。
148 |
149 | - **UpperError**: 上限误差。
150 |
151 | - **LowerError**: 下限误差。
152 |
153 |
154 | 输入参数中回归类型的具体值所代表的公式可以参考以下链接:
155 |
156 | [Time Series and Forecasting Formula](https://origin2.cdn.componentsource.com/sites/default/files/resources/dundas/538236/WinChart2005/Forecasting.html)
157 |
158 | 使用 `FinancialFormula` 的代码十分简单,只需创建一个临时的 `Chart` ,插入原始数据作为一个 `Series` ,然后调用 `DataManipulator.FinancialFormula` 即可,所有代码加起来也就 30 来行:
159 |
160 | ``` CS
161 | public double[] GetPredictData(int forecastingPoints, double[] points)
162 | {
163 | var tempChart = new Chart();
164 |
165 | tempChart.ChartAreas.Add(new ChartArea());
166 | tempChart.ChartAreas[0].AxisX = new Axis();
167 | tempChart.ChartAreas[0].AxisY = new Axis();
168 | tempChart.Series.Add(new Series());
169 |
170 | for (int i = 0; i < points.Length; i++)
171 | {
172 | tempChart.Series[0].Points.AddXY(i, points[i]);
173 | }
174 |
175 | var trendSeries = new Series();
176 | tempChart.Series.Add(trendSeries);
177 |
178 | var typeRegression = "Exponential";
179 | var forecasting = forecastingPoints.ToString();
180 | var error = "false";
181 | var forecastingError = "false";
182 | var parameters = typeRegression + ',' + forecasting + ',' + error + ',' + forecastingError;
183 |
184 | tempChart.DataManipulator.FinancialFormula(FinancialFormula.Forecasting, parameters, tempChart.Series[0], trendSeries);
185 |
186 | var result = new List();
187 | for (int i = 0; i < trendSeries.Points.Count; i++)
188 | {
189 | result.Add(trendSeries.Points[i].YValues[0]);
190 | }
191 |
192 | return result.ToArray();
193 | }
194 | ```
195 |
196 | 这里我使用了 `Exponential` (指数函数)作为回归类型,结果如下,看起来重复性很好,但是转折处比较生硬,导致最后在实际计算中不太理想。如果想要理想的结果,应该先尝试找出最合适的回归公式。
197 |
198 | 
199 |
200 |
201 | ## 6. 最后
202 |
203 | [Math.Net](https://www.mathdotnet.com/) 是一个强大的项目,这篇文章只介绍了它所有功能的冰山一角。想了解更多可以参考官方文档,或参考博客园上的文章,例如:
204 |
205 | [【目录】开源Math.NET基础数学类库使用总目录 - 数据之巅 - 博客园](https://www.cnblogs.com/asxinyu/p/Bolg_Category_For_MathNet.html)
206 |
207 | `FinancialFormula` 挺好玩的,但它和图表控件耦合在一起,用起来感觉有点邪门歪道,倒是通过它多少学会了一点财务公式。
208 |
209 | 话说回来当年微软的控件库都很上心嘛,现在微软都不会出这么良心的图表库了,逼我们买第三方控件。
210 |
211 | 
212 |
213 |
214 |
215 | ## 7. 参考
216 |
217 |
218 | [Math.NET Numerics](https://numerics.mathdotnet.com/)
219 |
220 | [Curve Fitting Linear Regression](https://numerics.mathdotnet.com/Regression.html)
221 |
222 | [【目录】开源Math.NET基础数学类库使用总目录 - 数据之巅 - 博客园](https://www.cnblogs.com/asxinyu/p/Bolg_Category_For_MathNet.html)
223 |
224 | [数据预测与曲线拟合 - 知乎](https://zhuanlan.zhihu.com/p/95277637)
225 |
226 | [Time Series and Forecasting Formula](https://origin2.cdn.componentsource.com/sites/default/files/resources/dundas/538236/WinChart2005/Forecasting.html)
227 |
228 | [DataManipulator Class (System.Web.UI.DataVisualization.Charting) Microsoft Docs](https://docs.microsoft.com/zh-cn/dotnet/api/system.web.ui.datavisualization.charting.datamanipulator?view=netframework-4.8&WT.mc_id=WD-MVP-5003763)
229 |
230 | [DataFormula.FinancialFormula Method (System.Windows.Forms.DataVisualization.Charting) Microsoft Docs](https://docs.microsoft.com/zh-cn/dotnet/api/system.windows.forms.datavisualization.charting.dataformula.financialformula?view=netframework-4.8&WT.mc_id=WD-MVP-5003763)
231 |
232 | [FinancialFormula Enum (System.Windows.Forms.DataVisualization.Charting) Microsoft Docs](https://docs.microsoft.com/zh-cn/dotnet/api/system.windows.forms.datavisualization.charting.financialformula?view=netframework-4.8&WT.mc_id=WD-MVP-5003763)
233 |
234 | [how to generate graphs using Microsoft Chart Control ](http://www.nullskull.com/q/10352018/how-to-generate-graphs-using-microsoft-chart-control.aspx)
235 |
--------------------------------------------------------------------------------
/SimpleDataPrediction.sln:
--------------------------------------------------------------------------------
1 |
2 | Microsoft Visual Studio Solution File, Format Version 12.00
3 | # Visual Studio Version 16
4 | VisualStudioVersion = 16.0.30204.135
5 | MinimumVisualStudioVersion = 10.0.40219.1
6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SimpleDataPrediction", "SimpleDataPrediction\SimpleDataPrediction.csproj", "{CB3ADB0D-B3FA-476D-9A7D-A87D260F3376}"
7 | EndProject
8 | Global
9 | GlobalSection(SolutionConfigurationPlatforms) = preSolution
10 | Debug|Any CPU = Debug|Any CPU
11 | Release|Any CPU = Release|Any CPU
12 | EndGlobalSection
13 | GlobalSection(ProjectConfigurationPlatforms) = postSolution
14 | {CB3ADB0D-B3FA-476D-9A7D-A87D260F3376}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
15 | {CB3ADB0D-B3FA-476D-9A7D-A87D260F3376}.Debug|Any CPU.Build.0 = Debug|Any CPU
16 | {CB3ADB0D-B3FA-476D-9A7D-A87D260F3376}.Release|Any CPU.ActiveCfg = Release|Any CPU
17 | {CB3ADB0D-B3FA-476D-9A7D-A87D260F3376}.Release|Any CPU.Build.0 = Release|Any CPU
18 | EndGlobalSection
19 | GlobalSection(SolutionProperties) = preSolution
20 | HideSolutionNode = FALSE
21 | EndGlobalSection
22 | GlobalSection(ExtensibilityGlobals) = postSolution
23 | SolutionGuid = {966A4A94-7645-4908-8CEF-45DAB767015C}
24 | EndGlobalSection
25 | EndGlobal
26 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/App.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/Datas.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.IO;
4 | using System.Linq;
5 | using System.Text;
6 | using System.Threading.Tasks;
7 |
8 | namespace SimpleDataPrediction
9 | {
10 | public class Datas
11 | {
12 | public List> LoadSourceDatas()
13 | {
14 | var allLines = File.ReadAllLines(Path.Combine(Environment.CurrentDirectory, "data.txt"));
15 |
16 | var sourceDatas = new List>();
17 |
18 | foreach (var line in allLines)
19 | {
20 | sourceDatas.Add(line.Split('\t').Select(l => double.Parse(l)).ToList());
21 | }
22 |
23 | return sourceDatas;
24 | }
25 |
26 | public void SaveResultDatas( List> resultDatas,string fileName)
27 | {
28 | var result = string.Empty;
29 |
30 | foreach (var line in resultDatas)
31 | {
32 | result += string.Join("\t", line);
33 | result += Environment.NewLine;
34 | }
35 |
36 | File.WriteAllText(Path.Combine(Environment.CurrentDirectory, fileName), result);
37 | }
38 |
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/Forecaster.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Windows;
5 | using System.Windows.Forms.DataVisualization.Charting;
6 |
7 | namespace SimpleDataPrediction
8 | {
9 | public class Forecaster
10 | {
11 | public double[] GetPredictData(int forecastingPoints, double[] points)
12 | {
13 | var tempChart = new Chart();
14 |
15 | tempChart.ChartAreas.Add(new ChartArea());
16 | tempChart.ChartAreas[0].AxisX = new Axis();
17 | tempChart.ChartAreas[0].AxisY = new Axis();
18 | tempChart.Series.Add(new Series());
19 |
20 | for (int i = 0; i < points.Length; i++)
21 | {
22 | tempChart.Series[0].Points.AddXY(i, points[i]);
23 | }
24 |
25 | var trendSeries = new Series();
26 | tempChart.Series.Add(trendSeries);
27 |
28 | var typeRegression = "Exponential";
29 | var forecasting = forecastingPoints.ToString();
30 | var error = "false";
31 | var forecastingError = "false";
32 | var parameters = typeRegression + ',' + forecasting + ',' + error + ',' + forecastingError;
33 |
34 | tempChart.DataManipulator.FinancialFormula(FinancialFormula.Forecasting, parameters, tempChart.Series[0], trendSeries);
35 |
36 | var result = new List();
37 | for (int i = 0; i < trendSeries.Points.Count; i++)
38 | {
39 | result.Add(trendSeries.Points[i].YValues[0]);
40 | }
41 |
42 | return result.ToArray();
43 | }
44 | }
45 | }
46 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/GaussNewton.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Text;
5 | using System.Threading.Tasks;
6 |
7 | namespace SimpleDataPrediction
8 | {
9 | ///
10 | /// https://bbs.csdn.net/topics/320245824
11 | ///
12 | public class GaussNewton
13 | {
14 | public delegate double F(double[] coefficients, double x);
15 |
16 | /// Construct a GaussNewton solver
17 | public GaussNewton(int coefficientCount)
18 | {
19 | this.coefficientCount = coefficientCount;
20 | this.coefficients = new double[coefficientCount];
21 | }
22 |
23 | /// Initialize the solver without a guess. Y = f(X)
24 | public void Initialize(double[] Y, double[] X, F f)
25 | {
26 | Initialize(Y, X, f, null);
27 | }
28 |
29 | /// Initialize the solver: Y = f(X) with a guessed approximation
30 | public void Initialize(double[] Y, double[] X, F f, double[] coefficientGuess)
31 | {
32 | if (X == null || Y == null || f == null) throw new ArgumentNullException();
33 | if (X.Length != Y.Length) throw new ArgumentException("Y and X not in pairs");
34 |
35 | this.xs = X;
36 | this.ys = Y;
37 | this.function = f;
38 | this.solved = false;
39 |
40 | if (coefficientGuess != null && coefficientGuess.Length == this.coefficientCount)
41 | {
42 | Array.Copy(coefficientGuess, this.coefficients, this.coefficientCount);
43 | }
44 | }
45 |
46 | /// Get the solved coefficents
47 | /// Throw when not answer can be found
48 | public double[] Coefficients
49 | {
50 | get { if (!this.solved) { Solve(); } return this.coefficients; }
51 | }
52 |
53 | /// Get the residual error (SSE)
54 | public double SumOfSquredError
55 | {
56 | get { return this.sse; }
57 | }
58 |
59 | /// Iteratively solve the coefficients using Gauss-Newton method
60 | /// http://en.wikipedia.org/wiki/Gauss%E2%80%93Newton_algorithm
61 | public double[] Solve()
62 | {
63 | if (this.ys == null) throw new InvalidOperationException("Not yet initialized");
64 |
65 | double lastSSE = double.MaxValue;
66 | double[] errors = new double[this.ys.Length];
67 |
68 | // let C0 be the current coefficient guess, C1 be the better answer we are after
69 | // let E0 be the error using current guess
70 | // we have:
71 | // JacT * Jac * (C1 - C0) = JacT * E0
72 | //
73 | MyMatrix jacobian = Jacobian();
74 | MyMatrix jacobianT = jacobian.Transpose();
75 | MyMatrix product = jacobianT * jacobian;
76 | SquareMatrix inverse = SquareMatrix.FromMatrix(product).Inverse();
77 |
78 | for (int iteration = 0; iteration < GaussNewton.MaxIteration; iteration++)
79 | {
80 | this.sse = 0;
81 |
82 | for (int i = 0; i < this.ys.Length; i++)
83 | {
84 | double y = function(this.coefficients, this.xs[i]);
85 | errors[i] = this.ys[i] - y;
86 | sse += errors[i] * errors[i];
87 | }
88 |
89 | if (lastSSE - sse < GaussNewton.ConvergeThreshold)
90 | {
91 | this.solved = true;
92 | return this.coefficients;
93 | }
94 |
95 | double[] shift = inverse * (jacobianT * errors);
96 |
97 | for (int i = 0; i < this.coefficientCount; i++)
98 | {
99 | this.coefficients[i] += shift[i];
100 | }
101 |
102 | lastSSE = sse;
103 | }
104 | throw new InvalidOperationException("No answer can be found");
105 | }
106 |
107 | /// Calculate a Jacobian matrix.
108 | /// http://en.wikipedia.org/wiki/Jacobian_matrix_and_determinant
109 | private MyMatrix Jacobian()
110 | {
111 | double[][] p = new double[this.coefficientCount][];
112 | for (int i = 0; i < p.Length; i++)
113 | {
114 | p[i] = new double[this.coefficientCount];
115 | p[i][i] = 1;
116 | }
117 |
118 | MyMatrix jacobian = new MyMatrix(this.ys.Length, this.coefficientCount);
119 | for (int i = 0; i < this.ys.Length; i++)
120 | {
121 | for (int j = 0; j < this.coefficientCount; j++)
122 | {
123 | jacobian[i, j] = function(p[j], this.xs[i]);
124 | }
125 | }
126 | return jacobian;
127 | }
128 |
129 | private bool solved;
130 | private int coefficientCount;
131 | private double[] coefficients;
132 | private double[] xs;
133 | private double[] ys;
134 | private double sse;
135 | private F function;
136 |
137 | public static readonly int MaxIteration = 16;
138 | public static readonly double Epsilon = 1e-10;
139 | public static readonly double ConvergeThreshold = 1e-8;
140 | }
141 | }
142 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/MyMatrix.cs:
--------------------------------------------------------------------------------
1 | using System;
2 |
3 | namespace SimpleDataPrediction
4 | {
5 | public class MyMatrix
6 | {
7 | private int cols, rows;
8 | protected double[,] data;
9 |
10 | /// Construct a matrix
11 | public MyMatrix(int rows, int cols)
12 | {
13 | this.rows = rows;
14 | this.cols = cols;
15 | this.data = new double[rows, cols];
16 | }
17 |
18 | /// Construct a matrix by copying the data
19 | public MyMatrix(double[,] data) : this(data.GetLength(0), data.GetLength(1))
20 | {
21 | System.Buffer.BlockCopy(data, 0, this.data, 0, sizeof(double) * this.rows * this.cols);
22 | }
23 |
24 | /// Gets the number of rows in the matrix
25 | public int Rows { get { return this.rows; } }
26 |
27 | /// Gets the number of columns in the matrix
28 | public int Cols { get { return this.cols; } }
29 |
30 | /// Gets the raw data of the matrix. Should be treated as readonly
31 | public double[,] RawData { get { return this.data; } }
32 |
33 | /// Gets the sets the matrix element
34 | public double this[int row, int col]
35 | {
36 | get { return this.data[row, col]; }
37 | set { this.data[row, col] = value; }
38 | }
39 |
40 | /// Multiply by a vector. The width of the matrix should equal the height of the vector
41 | public double[] Multiply(double[] x)
42 | {
43 | if (x == null || x.Length != this.cols) throw new ArgumentException("Invalid vector");
44 | double[] result = new double[this.rows];
45 |
46 | for (int i = 0; i < result.Length; i++)
47 | {
48 | double sum = 0;
49 | for (int j = 0; j < this.cols; j++)
50 | {
51 | sum += this.data[i, j] * x[j];
52 | }
53 | result[i] = sum;
54 | }
55 | return result;
56 | }
57 |
58 | /// Multiply by another matrix. The width of left matrix should equal the height of right matrix
59 | public MyMatrix Multiply(MyMatrix m)
60 | {
61 | if (m == null || m.rows != this.cols) throw new ArgumentException("Invalid matrix to multiply");
62 | MyMatrix result = new MyMatrix(this.rows, m.cols);
63 | int inner = this.cols;
64 |
65 | for (int row = 0; row < result.rows; row++)
66 | {
67 | for (int col = 0; col < result.cols; col++)
68 | {
69 | double sum = 0;
70 | for (int i = 0; i < inner; i++) sum += this[row, i] * m[i, col];
71 | result[row, col] = sum;
72 | }
73 | }
74 | return result;
75 | }
76 |
77 | /// Create a transposed matrix
78 | public MyMatrix Transpose()
79 | {
80 | MyMatrix result = new MyMatrix(this.cols, this.rows);
81 | for (int row = 0; row < this.rows; row++)
82 | {
83 | for (int col = 0; col < this.cols; col++)
84 | {
85 | result[col, row] = this.data[row, col];
86 | }
87 | }
88 | return result;
89 | }
90 |
91 | public static double[] operator *(MyMatrix m, double[] vector)
92 | {
93 | return m.Multiply(vector);
94 | }
95 |
96 | public static MyMatrix operator *(MyMatrix m1, MyMatrix m2)
97 | {
98 | return m1.Multiply(m2);
99 | }
100 | }
101 | }
102 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/Program.cs:
--------------------------------------------------------------------------------
1 | using MathNet.Numerics;
2 | using System;
3 | using System.Collections.Generic;
4 | using System.Linq;
5 | using System.Text;
6 | using System.Threading.Tasks;
7 |
8 | namespace SimpleDataPrediction
9 | {
10 | class Program
11 | {
12 | static void Main(string[] args)
13 | {
14 | try
15 | {
16 | FinancialFormulaTest();
17 | PolynomialTest();
18 | MathNetTest();
19 | Console.WriteLine("Analysis completed");
20 | }
21 | catch (Exception ex)
22 | {
23 | Console.WriteLine(ex.Message);
24 | }
25 | Console.ReadLine();
26 | }
27 |
28 | private static void FinancialFormulaTest()
29 | {
30 | //var source = "5.857486213 6.882938361 5.938018732 7.418233591 8.102131936 10.02132021 11.30071133 13.07283147 15.03172119 17.62765193 20.33497935 23.3258717 26.49699319 29.9783162 32.92265494 35.10837941 36.3501758 36.53764154 34.1757566 30.89822951 26.63771337 22.32763029 18.38308201 14.90463905 12.35598901 9.741861183 7.720235644 6.033749358 4.565486063 3.445948379 2.494921555 1.82715694 1.368045582 0.965480591 0.722276257 0.577920119 0.448848566 0.361900586 0.29215714 0.242289617 0.202792727 0.166097863 0.069075582 0.002831501 0.000875038 0.043841538";
31 | var datas = new Datas();
32 | var sourceDatas = datas.LoadSourceDatas();
33 | foreach (var data in sourceDatas)
34 | {
35 | var values = data.Skip(32).Take(6);
36 |
37 | var range = Enumerable.Range(1, 6).Select(r => (double)r);
38 | var forecaster = new Forecaster();
39 | var result = forecaster.GetPredictData(8, values.ToArray());
40 |
41 | for (int i = 0; i < 8; i++)
42 | {
43 | data[data.Count - 1 - i] = result[result.Length - 1 - i];
44 | }
45 |
46 | SetUnitary(data);
47 | }
48 |
49 | datas.SaveResultDatas(sourceDatas, "PredictData.txt");
50 | }
51 |
52 | private static void PolynomialTest()
53 | {
54 | //var source = "5.857486213 6.882938361 5.938018732 7.418233591 8.102131936 10.02132021 11.30071133 13.07283147 15.03172119 17.62765193 20.33497935 23.3258717 26.49699319 29.9783162 32.92265494 35.10837941 36.3501758 36.53764154 34.1757566 30.89822951 26.63771337 22.32763029 18.38308201 14.90463905 12.35598901 9.741861183 7.720235644 6.033749358 4.565486063 3.445948379 2.494921555 1.82715694 1.368045582 0.965480591 0.722276257 0.577920119 0.448848566 0.361900586 0.29215714 0.242289617 0.202792727 0.166097863 0.069075582 0.002831501 0.000875038 0.043841538";
55 | //var range = string.Join("\r\n", Enumerable.Range(1, 14));
56 | var datas = new Datas();
57 | var sourceDatas = datas.LoadSourceDatas();
58 | foreach (var data in sourceDatas)
59 | {
60 | var values = data.Skip(32).Take(6);
61 |
62 | double[] X = Enumerable.Range(1, 6).Select(r => (double)r).ToArray();
63 | double[] Y = values.ToArray();
64 |
65 | // f(x) = A*x*x + B*x + C
66 | GaussNewton.F f = delegate (double[] coefficients, double x)
67 | {
68 | return coefficients[0] * x * x + coefficients[1] * x + coefficients[2];
69 | };
70 |
71 | GaussNewton gaussNewton = new GaussNewton(3);
72 | gaussNewton.Initialize(Y, X, f);
73 | double[] answer = gaussNewton.Coefficients;
74 |
75 | List result = new List();
76 | for (int i = 1; i < 15; i++)
77 | {
78 | result.Add(answer[0] * i * i + answer[1] * i + answer[2]);
79 | }
80 |
81 | for (int i = 0; i < 8; i++)
82 | {
83 | data[data.Count - 1 - i] = result[result.Count - 1 - i];
84 | }
85 |
86 | SetUnitary(data);
87 | }
88 |
89 | datas.SaveResultDatas(sourceDatas, "PolynomialData.txt");
90 | }
91 |
92 | private static void MathNetTest()
93 | {
94 | var datas = new Datas();
95 | var sourceDatas = datas.LoadSourceDatas();
96 | foreach (var data in sourceDatas)
97 | {
98 | var values = data.Skip(32).Take(6);
99 |
100 | double[] X = Enumerable.Range(1, 6).Select(r => (double)r).ToArray();
101 | double[] Y = values.ToArray();
102 |
103 | double[] parameters = Fit.Polynomial(X, Y, 2);
104 |
105 |
106 | List result = new List();
107 | for (int i = 1; i < 15; i++)
108 | {
109 | result.Add(parameters[0] + parameters[1] * i + parameters[2] * i * i );
110 | }
111 |
112 | for (int i = 0; i < 8; i++)
113 | {
114 | data[data.Count - 1 - i] = result[result.Count - 1 - i];
115 | }
116 |
117 | SetUnitary(data);
118 | }
119 |
120 | datas.SaveResultDatas(sourceDatas, "MathNetData.txt");
121 | }
122 |
123 | private static void SetUnitary(List dataToSet)
124 | {
125 | if (dataToSet != null
126 | && dataToSet.Count > 0)
127 | {
128 | var totalDistribution = dataToSet.Sum();
129 |
130 | if (totalDistribution > 0)
131 | for (var i = 0; i < dataToSet.Count; i++)
132 | dataToSet[i] = dataToSet[i] / totalDistribution;
133 | }
134 | }
135 | }
136 | }
137 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.CompilerServices;
3 | using System.Runtime.InteropServices;
4 |
5 | // 有关程序集的一般信息由以下
6 | // 控制。更改这些特性值可修改
7 | // 与程序集关联的信息。
8 | [assembly: AssemblyTitle("SimpleDataPrediction")]
9 | [assembly: AssemblyDescription("")]
10 | [assembly: AssemblyConfiguration("")]
11 | [assembly: AssemblyCompany("")]
12 | [assembly: AssemblyProduct("SimpleDataPrediction")]
13 | [assembly: AssemblyCopyright("Copyright © 2020")]
14 | [assembly: AssemblyTrademark("")]
15 | [assembly: AssemblyCulture("")]
16 |
17 | // 将 ComVisible 设置为 false 会使此程序集中的类型
18 | //对 COM 组件不可见。如果需要从 COM 访问此程序集中的类型
19 | //请将此类型的 ComVisible 特性设置为 true。
20 | [assembly: ComVisible(false)]
21 |
22 | // 如果此项目向 COM 公开,则下列 GUID 用于类型库的 ID
23 | [assembly: Guid("cb3adb0d-b3fa-476d-9a7d-a87d260f3376")]
24 |
25 | // 程序集的版本信息由下列四个值组成:
26 | //
27 | // 主版本
28 | // 次版本
29 | // 生成号
30 | // 修订号
31 | //
32 | //可以指定所有这些值,也可以使用“生成号”和“修订号”的默认值
33 | //通过使用 "*",如下所示:
34 | // [assembly: AssemblyVersion("1.0.*")]
35 | [assembly: AssemblyVersion("1.0.0.0")]
36 | [assembly: AssemblyFileVersion("1.0.0.0")]
37 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/SimpleDataPrediction.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Debug
6 | AnyCPU
7 | {CB3ADB0D-B3FA-476D-9A7D-A87D260F3376}
8 | Exe
9 | SimpleDataPrediction
10 | SimpleDataPrediction
11 | v4.7.2
12 | 512
13 | true
14 | true
15 |
16 |
17 | AnyCPU
18 | true
19 | full
20 | false
21 | bin\Debug\
22 | DEBUG;TRACE
23 | prompt
24 | 4
25 |
26 |
27 | AnyCPU
28 | pdbonly
29 | true
30 | bin\Release\
31 | TRACE
32 | prompt
33 | 4
34 |
35 |
36 |
37 | ..\packages\MathNet.Numerics.4.11.0\lib\net461\MathNet.Numerics.dll
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 | Always
67 |
68 |
69 |
70 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/SquareMatrix.cs:
--------------------------------------------------------------------------------
1 | using System;
2 |
3 | namespace SimpleDataPrediction
4 | {
5 | public class SquareMatrix : MyMatrix
6 | {
7 | int rank;
8 |
9 | /// Construct an identity matrix
10 | public SquareMatrix(int rank) : base(rank, rank)
11 | {
12 | this.rank = rank;
13 | for (int i = 0; i < rank; i++) this.data[i, i] = 1;
14 | }
15 |
16 | /// Construct a square matrix by copying the data
17 | public SquareMatrix(double[,] data) : base(data)
18 | {
19 | if (data.GetLength(0) != data.GetLength(1))
20 | {
21 | throw new ArgumentException("Only square matrix supported");
22 | }
23 | this.rank = data.GetLength(0);
24 | }
25 |
26 | /// Use Laplace expansion to calculate the determinant of a square matrix
27 | public double Determinant()
28 | {
29 | if (this.rank == 1)
30 | {
31 | return data[0, 0];
32 | }
33 | if (this.rank == 2)
34 | {
35 | return data[0, 0] * data[1, 1] - data[1, 0] * data[0, 1];
36 | }
37 |
38 | double det = 0;
39 | for (int i = 0; i < this.rank; i++)
40 | {
41 | det += this.data[i, 0] * this.Cofactor(i, 0).Determinant() * (i % 2 == 0 ? 1 : -1);
42 | }
43 | return det;
44 | }
45 |
46 | /// Use Cramer's rule to recursively find the inverse of a square matrix
47 | public SquareMatrix Inverse()
48 | {
49 | double det = this.Determinant();
50 | if (Math.Abs(det) < 1e-8) throw new InvalidOperationException("Cannot inverse a singular matrix");
51 |
52 | SquareMatrix result = new SquareMatrix(this.rank);
53 | for (int i = 0; i < this.rank; i++)
54 | {
55 | for (int j = 0; j < this.rank; j++)
56 | {
57 | result.data[j, i] = this.Cofactor(i, j).Determinant() * ((i + j) % 2 == 0 ? 1 : -1) / det;
58 | }
59 | }
60 | return result;
61 | }
62 |
63 | /// Get a Cofactor matrix
64 | public SquareMatrix Cofactor(int i, int j)
65 | {
66 | if (this.rank < 2) throw new InvalidOperationException("Rank is less than two");
67 |
68 | SquareMatrix result = new SquareMatrix(this.rank - 1);
69 | double[,] buf = result.data;
70 | for (int y = 0; y < this.rank; y++)
71 | {
72 | for (int x = 0; x < this.rank; x++)
73 | {
74 | if (y != i && x != j)
75 | {
76 | buf[y - (y > i ? 1 : 0), x - (x > j ? 1 : 0)] = this.data[y, x];
77 | }
78 | }
79 | }
80 | return result;
81 | }
82 |
83 | /// Create a square matrix from a general matrix
84 | public static SquareMatrix FromMatrix(MyMatrix m)
85 | {
86 | if (m == null || m.Cols != m.Rows) throw new ArgumentException("Not a valid square matrix");
87 | return new SquareMatrix(m.RawData);
88 | }
89 | }
90 | }
91 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/data.txt:
--------------------------------------------------------------------------------
1 | 7.54E-05 0 1.96E-06 0.000122474 0.000276277 0.00032527 0.000377681 0.000444025 0.000537549 0.000667915 0.000884025 0.001113903 0.001550972 0.002193355 0.003060919 0.004220457 0.005910079 0.008091797 0.010930101 0.014042115 0.018113312 0.022692503 0.028314453 0.034625866 0.043060621 0.051592362 0.061194118 0.06750829 0.073170593 0.072916025 0.07083148 0.065924991 0.060180064 0.053404088 0.046820985 0.04086167 0.034998027 0.029518564 0.024496241 0.019466762 0.014777455 0.008666923 0.002038376 0 0 0
2 | 7.63E-05 1.91E-07 4.05E-06 0.000124948 0.000291488 0.000345292 0.000407282 0.000482729 0.000595551 0.000737636 0.000960222 0.001213826 0.001669233 0.002363499 0.003247374 0.004453304 0.006180711 0.008247557 0.011090353 0.014266729 0.018124014 0.022676952 0.028306237 0.034343309 0.043040124 0.051147193 0.061038434 0.067338017 0.073195706 0.072972943 0.071024019 0.066261281 0.060410214 0.053585336 0.047097036 0.041154017 0.035126629 0.029605795 0.024411435 0.019231097 0.014296683 0.007980825 0.000874397 0 0 0
3 | 7.66E-05 7.06E-07 3.19E-06 0.00012269 0.000284844 0.000341307 0.000396447 0.000479126 0.000576307 0.000711824 0.000930306 0.001139596 0.00165219 0.002227548 0.003103584 0.004353086 0.006033162 0.008070523 0.010758566 0.014069041 0.018111836 0.02264814 0.028162319 0.034641845 0.042630832 0.051491248 0.060782993 0.067402502 0.072856615 0.072616362 0.070632267 0.066340129 0.060304267 0.053453543 0.046781865 0.040721651 0.034817812 0.029268195 0.024605224 0.019702151 0.01492732 0.009070091 0.002700118 0 0 0
4 | 7.78E-05 1.43E-06 4.15E-06 0.000124912 0.000294934 0.000353893 0.000414622 0.000502789 0.00060783 0.000749817 0.00097921 0.001189129 0.001725132 0.002314323 0.003256379 0.004458873 0.006197069 0.008248257 0.01088353 0.014180343 0.018293822 0.02275372 0.028171942 0.034695621 0.042768695 0.05153194 0.060927847 0.067274527 0.072737537 0.072368596 0.070355008 0.06598595 0.060079534 0.053144595 0.046659095 0.04055342 0.034692664 0.029157472 0.024534925 0.019736636 0.0150168 0.009064367 0.002930854 0 0 0
5 | 7.65E-05 6.73E-07 4.45E-06 0.000124483 0.000297432 0.000358746 0.000419878 0.000516853 0.000619463 0.00076451 0.000965871 0.001179395 0.001766617 0.002395241 0.003330698 0.004540381 0.006144652 0.0082582 0.010735737 0.013959981 0.018023413 0.022634471 0.027820073 0.034419551 0.042240213 0.051202119 0.0606522 0.067168309 0.072900723 0.072419283 0.070506488 0.066251507 0.060294686 0.053403543 0.04692542 0.040836041 0.034869813 0.029361481 0.024687133 0.019827212 0.015054175 0.009100952 0.002941422 0 0 0
6 | 7.39E-05 0 2.02E-06 0.000119534 0.000277453 0.000329976 0.000385794 0.000451915 0.000545482 0.000666653 0.000900511 0.001109042 0.001552518 0.002079337 0.002935448 0.004102624 0.005842454 0.007797771 0.010460276 0.013679877 0.017663543 0.022269747 0.027894539 0.034231729 0.04227365 0.050963154 0.060098404 0.067066378 0.072305186 0.072624451 0.070175807 0.066074304 0.060169081 0.053279822 0.046642647 0.040568496 0.03474091 0.029394627 0.024972632 0.02029305 0.016083836 0.010620602 0.00527313 0.001007708 0 0
7 | 7.58E-05 0 3.65E-06 0.000123394 0.000288954 0.000351686 0.000413353 0.00048409 0.000589854 0.000726371 0.000965126 0.001180027 0.001639907 0.002230193 0.003107555 0.004295323 0.006040871 0.008067466 0.010762137 0.013901911 0.018070023 0.022704695 0.028145776 0.034428492 0.042642105 0.051446566 0.060448181 0.067476633 0.072423329 0.073014526 0.070545729 0.06645498 0.060469042 0.053556326 0.046688387 0.040544312 0.034666346 0.029335764 0.024716842 0.019804645 0.015150977 0.009149993 0.002868665 0 0 0
8 | 7.64E-05 5.18E-07 5.45E-06 0.000125214 0.000292816 0.00036263 0.000429935 0.000508035 0.000626811 0.000757767 0.00102005 0.001254548 0.001696777 0.002387239 0.003270766 0.004505161 0.006180696 0.008192333 0.01095047 0.013980929 0.018043543 0.022678148 0.027992425 0.03437616 0.042463175 0.050967939 0.059984314 0.066584203 0.071754902 0.072303591 0.069969556 0.065885605 0.059731137 0.053025357 0.046210986 0.040262507 0.034450755 0.029144516 0.024843117 0.020175985 0.01600763 0.01051412 0.005034266 0.000971554 0 0
9 | 8.05E-05 1.07E-05 6.56E-06 0.000116638 0.000267613 0.000324131 0.000381441 0.000436766 0.000533054 0.000651819 0.000878576 0.001096007 0.001509789 0.002044066 0.002783771 0.004121335 0.005413986 0.007627017 0.010298239 0.013556572 0.017069031 0.021241895 0.027325235 0.033834451 0.041119943 0.04946145 0.058740421 0.064651265 0.07015542 0.069843805 0.067662233 0.063660589 0.057910716 0.05128763 0.045082901 0.039200782 0.033691066 0.028650003 0.024987946 0.021196664 0.018135649 0.013507067 0.011165115 0.00798112 0.006243563 0.00405543
10 | 8.36E-05 1.39E-05 8.95E-06 0.000120693 0.000283392 0.000345194 0.000407533 0.000469548 0.000579946 0.000711705 0.000933267 0.001132584 0.001622284 0.002144362 0.002793608 0.004152736 0.005439491 0.007719602 0.010403062 0.01381884 0.017555457 0.021246806 0.02776885 0.034701603 0.042099313 0.050231332 0.060029564 0.066057352 0.071473591 0.071082673 0.069143469 0.064897218 0.059003597 0.052197976 0.045803066 0.039890931 0.034142174 0.028835867 0.025026547 0.020976687 0.017470579 0.012128861 0.008813211 0.004974772 0.001264187 0
11 | 8.45E-05 1.43E-05 9.62E-06 0.000125075 0.000291855 0.000358277 0.000421667 0.000476968 0.000597543 0.000747128 0.001020048 0.001212235 0.001670814 0.002234258 0.002876359 0.004195063 0.005532207 0.007947504 0.010760164 0.013859894 0.017829954 0.021372298 0.028079505 0.035065361 0.042317062 0.050537627 0.06061759 0.066185871 0.071775743 0.070568903 0.068688281 0.064407445 0.05855506 0.051803068 0.045279396 0.03959753 0.033908041 0.028710564 0.024899886 0.020960459 0.017507161 0.011865399 0.008631041 0.004703434 0.001697891 0
12 | 7.01E-05 5.82E-07 2.33E-06 0.000107476 0.00027006 0.000323546 0.000380172 0.000455354 0.000554811 0.000656593 0.000831513 0.001028749 0.001480521 0.002008332 0.002728354 0.003770878 0.005327512 0.007371145 0.009871282 0.012705609 0.016487783 0.021090486 0.026491496 0.032448317 0.040361023 0.048498062 0.057339071 0.06371399 0.068647032 0.068441028 0.066485666 0.062525633 0.056716714 0.050295042 0.044278245 0.038571854 0.033414474 0.028527109 0.024739342 0.021448663 0.018868656 0.015177161 0.013394551 0.010907734 0.011039824 0.010146142
13 | 6.67E-05 0 5.43E-07 0.00010764 0.000277478 0.000332508 0.000396765 0.000472497 0.000570705 0.000685292 0.000856704 0.001064029 0.001529604 0.002095634 0.002804101 0.003863139 0.005467571 0.007450873 0.010163902 0.012849286 0.016463125 0.020967798 0.026786323 0.032591312 0.040725429 0.048814996 0.057713374 0.063791989 0.068938073 0.068554374 0.06659642 0.062507822 0.056598045 0.050275758 0.044279573 0.038526042 0.033349524 0.028301524 0.024519918 0.021417398 0.018642359 0.014762841 0.013046619 0.010380285 0.010840471 0.009553613
14 | 6.59E-05 0 1.62E-07 0.000110031 0.000283987 0.000341208 0.000415174 0.000490093 0.000600085 0.000714397 0.000863399 0.001055099 0.001537841 0.002162326 0.002923048 0.004032418 0.005711975 0.007606366 0.010379892 0.013005352 0.016561154 0.021431848 0.027313586 0.033334749 0.041789491 0.050133515 0.059247861 0.065880047 0.070837699 0.070535315 0.068554309 0.064581005 0.058398883 0.052164862 0.046055101 0.039902005 0.034567672 0.029076311 0.024837953 0.021314455 0.017801808 0.013193495 0.009934262 0.007000502 0.0032441 9.30E-06
15 | 7.09E-05 0 3.51E-07 0.000108516 0.000270508 0.000323725 0.000370546 0.000436827 0.00052603 0.000649692 0.000795701 0.001003671 0.001432336 0.001881439 0.002663988 0.003833906 0.005325085 0.007282652 0.010203432 0.013027216 0.017021046 0.021690658 0.027077336 0.033595201 0.041728035 0.05021308 0.059152078 0.065355031 0.070432383 0.070681136 0.068166232 0.064475277 0.058177727 0.051769701 0.045257439 0.039538748 0.033904411 0.028932007 0.024837436 0.020822446 0.017546573 0.013402531 0.010651188 0.007694627 0.005327165 0.002343945
16 | 6.82E-05 0 0 0.000108388 0.000271496 0.000329173 0.000373158 0.000445096 0.00052809 0.000655044 0.000806211 0.000996016 0.001410279 0.001931915 0.002656115 0.003742621 0.005277139 0.007179286 0.010172842 0.013007787 0.017014288 0.021537837 0.026949791 0.033353099 0.041585408 0.049800079 0.058863057 0.065242818 0.070314185 0.070757175 0.068213598 0.064415465 0.058244024 0.052004505 0.045342193 0.039652635 0.033900822 0.02877864 0.024875191 0.020849582 0.017522389 0.013504833 0.010813788 0.007982311 0.005723716 0.002799676
17 | 6.88E-05 0 2.23E-07 0.000110967 0.000280733 0.000339713 0.000387848 0.000466702 0.000556086 0.000687914 0.000872762 0.001061145 0.001461009 0.001985214 0.002699155 0.003760449 0.005291068 0.007455688 0.010362512 0.013371622 0.017307773 0.022015608 0.027390956 0.034108351 0.042416161 0.050697495 0.05987286 0.066518555 0.071597391 0.072022177 0.069876873 0.065617914 0.059572012 0.053473556 0.046377996 0.0405578 0.034525996 0.029123703 0.024933961 0.020429844 0.016537352 0.011976494 0.007666601 0.004162924 0 0
18 | 7.81E-05 1.81E-06 5.68E-06 0.000116939 0.000282821 0.000345458 0.000410423 0.000489847 0.000608492 0.000749184 0.00097672 0.001238877 0.001706003 0.002399841 0.003276744 0.004525228 0.006208746 0.008294153 0.010904985 0.01405679 0.017893775 0.022375959 0.027805992 0.034032604 0.041849659 0.050404825 0.059242162 0.066025737 0.071267363 0.071067582 0.068804441 0.064897085 0.058927824 0.05241739 0.045890824 0.040011269 0.034479129 0.029189199 0.024893973 0.020658421 0.016944978 0.012106403 0.008040877 0.004095675 0 0
19 | 7.92E-05 2.47E-06 6.79E-06 0.000118837 0.000292474 0.000362931 0.000435616 0.000524631 0.000649848 0.000803424 0.0010239 0.001294106 0.001821845 0.002577614 0.003483366 0.004767019 0.006447163 0.0085328 0.01115905 0.014298166 0.018062491 0.022427275 0.027816891 0.033970406 0.041655268 0.050340449 0.058958109 0.065617514 0.07065599 0.070330216 0.068119687 0.064231933 0.058198241 0.051841691 0.045471335 0.039616397 0.034060776 0.028980775 0.024828341 0.020744025 0.017243765 0.012562754 0.008882211 0.005143116 0.001559063 0
20 |
--------------------------------------------------------------------------------
/SimpleDataPrediction/packages.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
--------------------------------------------------------------------------------