gpt4 book ai didi

c# - MS Chart 中的插值实现

转载 作者:太空狗 更新时间:2023-10-29 20:42:06 28 4
gpt4 key购买 nike

我需要在 Windows 应用程序的 Ms-Chart 中实现插值和外插。

对于插值,我使用“MathNet”库。但我仍然不知道要实现这一点。

我尝试按如下方式实现插值。

using MathNet.Numerics.Interpolation.Algorithms;

NevillePolynomialInterpolation objIterpolate = new NevillePolynomialInterpolation(Xpoints, Ypoints);

double NewYValue;
NewYValue = Math.Abs(objIterpolate.Interpolate(newValue);

我在 NevillePolynomialInterpolation() 中传入 XPoints 作为第一个参数,它是我图表的 XValues 数组。和 Ypoints 作为我图表的 YValues 数组。

我将 newValue 作为 XValue 传递以获取插值。

任何人都可以建议,这是正确的方法还是建议实现插值的正确方法。

最佳答案

我设法创建了一个简短的示例,如果我在下面粘贴的代码适合您,请告诉我。

我不太习惯使用 MathDotNet 库,但是 XML 文档已经足够了,所以学习曲线并不陡峭,只是另一个 .NET 库和许多其他库。

否则你仍然可以去图书馆网站看看他们的文档,除了几个我不确定包含插值的例子,你可能会发现与你通过阅读 XML 文档得到的相同的东西.您还可以查看 github 并查看您要处理的插值的实现。

当然,如果您坚持此处描述的算法,您也可以尝试从头开始实现:http://en.wikipedia.org/wiki/Neville%27s_algorithm

无论如何,我假设您想利用 MathDotNet 库执行 Neville 多项式插值并在同一图表区域显示原始数据和插值数据。

关于附加信息,一些可以在这里找到(仍然不要期望那么多):

关于 MS Chart,就像处理任何其他 Winforms 控件一样,只需查看文档,如果有什么棘手的地方,请指出对您来说困难的地方,我会尽力为您解释清楚。

到目前为止,老实说,我对您不了解的内容有些挣扎,是 MS Chart、MathDotNet 还是两者?哪一个对您来说是个问题?

无论如何,没有什么特别的,只是将您的 X 和 Y 点传递给 MathDotNet 库(只要 Xs 和 Ys 的底层实现像数组 IEnumerable<T> 一样实现 T[] 就可以了)。

然后图书馆会为你做所有的数学,你只需要使用 Interpolate(...)给定的插值方法(您必须了解这里的插值意味着一种插值引擎,有点)。

我假设在您的代码片段中:XPointsYPoints都是IEnumerable<T>集合(因为你提到它们是数组)其中 TDouble 的一种, Single或任何适合您的 .NET Number Primitive。

// Copyright: Nothing At All License
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Diagnostics;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Windows.Forms.DataVisualization.Charting;
using MathNet.Numerics.Random;

namespace HelpSO
{
public static class Program
{
[STAThread]
public static void Main(params String[] arguments)
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);

var mainForm = new MainForm();

Application.Run(mainForm);
}
}

/// <summary>
/// Main Form.
/// </summary>
public class MainForm : Form
{
/// <summary>
/// Initializes the chart and cosmetics, make-up, glamour, etc..
/// </summary>
/// <returns>The chart.</returns>
private static Chart InitializeChart()
{
var chart = new Chart()
{
Dock = DockStyle.Fill,
};

const String defaultChartAreaName = @"Default";
const String defaultLegendName = @"Default";
const String defaultTitleName = @"Default";

var chartArea = chart.ChartAreas.Add(defaultChartAreaName);

var labelFont = new Font(@"Tahoma", 8f);

var axisX = chartArea.AxisX;
var axisY = chartArea.AxisY;

axisX.Title = @"X";
axisY.Title = @"Y";

axisX.LabelStyle.Format = axisX.LabelStyle.Format = "F4";

axisX.TitleFont = axisY.TitleFont = labelFont;
axisX.LabelStyle.Font = axisY.LabelStyle.Font = labelFont;

axisX.TitleAlignment = axisY.TitleAlignment = StringAlignment.Far;
axisX.MajorGrid.Enabled = axisY.MajorGrid.Enabled = true;
axisX.MinorGrid.Enabled = axisY.MinorGrid.Enabled = true;
axisX.MinorGrid.LineDashStyle = axisY.MinorGrid.LineDashStyle = ChartDashStyle.Dash;
axisX.MinorGrid.LineColor = axisY.MinorGrid.LineColor = Color.Gainsboro;

var legend = chart.Legends.Add(defaultLegendName);
legend.TitleSeparator = LegendSeparatorStyle.ThickGradientLine;
legend.BorderColor = Color.Black;
legend.Title = "Legend";

var title = chart.Titles.Add(defaultTitleName);
title.Text = @"My Awesome interpolated data";
title.Font = new Font(title.Font.FontFamily, 12f);

MainForm.InitializeChartSeries(chart);

return chart;
}

/// <summary>
/// Initializes the chart series and related data (raw and interpolated).
/// </summary>
/// <param name="chart">Chart.</param>
private static void InitializeChartSeries(Chart chart)
{
const String rawDataSeriesName = @"Raw Data";
const String interpolatedDataSeriesName = @"Interpolated Data";

var rawDataSeries = chart.Series.Add(rawDataSeriesName);
var interpolatedDataSeriesSeries = chart.Series.Add(interpolatedDataSeriesName);

rawDataSeries.ChartType = SeriesChartType.FastLine;
interpolatedDataSeriesSeries.ChartType = SeriesChartType.Spline;

rawDataSeries.BorderWidth = interpolatedDataSeriesSeries.BorderWidth = 2;

var rawDataPoints = DataFactory.GenerateDummySine(10, 1, 0.25);
var interpolatedDataPoints = DataFactory.Interpolate(rawDataPoints, 10);

rawDataSeries.Points.DataBind(rawDataPoints, @"X", @"Y", String.Empty);
interpolatedDataSeriesSeries.Points.DataBind(interpolatedDataPoints, @"X", @"Y", String.Empty);
}

/// <summary>
/// Initializes a new instance of the <see cref="HelpSO.MainForm"/> class.
/// </summary>
public MainForm()
{
this.StartPosition = FormStartPosition.CenterScreen;

var chart = MainForm.InitializeChart();

this.Controls.Add(chart);
}
}

/// <summary>
/// Data Factory.
/// </summary>
public static class DataFactory
{
/// <summary>
/// Generates a dummy sine.
/// </summary>
/// <returns>The dummy sine.</returns>
/// <param name="count">Count.</param>
/// <param name="amplitude">Amplitude.</param>
/// <param name="noiseAmplitude">Noise amplitude.</param>
public static IList<Point2D<Double, Double>> GenerateDummySine(UInt16 count, Double amplitude, Double noiseAmplitude)
{
if (count < 2)
{
throw new ArgumentOutOfRangeException(@"count");
}
else
{
var dummySinePoints = new List<Point2D<Double, Double>>();

var random = new Random();

var xStep = 1.0 / count;

for (var x = 0.0; x < 1.0; x += xStep)
{
var y = amplitude * Math.Sin(2f * Math.PI * x) + random.NextDouble() * noiseAmplitude;

var dummySinePoint = new Point2D<Double, Double>(x, y);

dummySinePoints.Add(dummySinePoint);
}

return dummySinePoints;
}
}

/// <summary>
/// Interpolate the specified source.
/// </summary>
/// <param name="source">Source.</param>
/// <param name="countRatio">Count ratio.</param>
public static IList<Point2D<Double, Double>> Interpolate(IList<Point2D<Double, Double>> source, UInt16 countRatio)
{
if (countRatio == 0)
{
throw new ArgumentOutOfRangeException(@"countRatio");
}
else if (source.Count < 2)
{
throw new ArgumentOutOfRangeException(@"source");
}
else
{

var rawDataPointsX = source.Select(item => item.X);
var rawDataPointsY = source.Select(item => item.Y);

// Could be done within one loop only... so far I'm pretty busy will update that example later
var xMin = rawDataPointsX.Min();
var xMax = rawDataPointsX.Max();

// Different Kinds of interpolation here... it's all up to you o pick up the one that's gonna match your own situation
// var interpolation = MathNet.Numerics.Interpolation.NevillePolynomialInterpolation.Interpolate(rawDataPointsX, rawDataPointsY);
var interpolation = MathNet.Numerics.Interpolation.CubicSpline.InterpolateNatural(rawDataPointsX, rawDataPointsY);

var listCopy = source.ToList();

var xStep = (xMax - xMin) / (source.Count * countRatio);

for (var x = xMin; x <= xMax; x += xStep)
{
var y = interpolation.Interpolate(x);

var point2D = new Point2D<Double, Double>(x, y);

listCopy.Add(point2D);
}

return listCopy;
}
}
}

// C# lacks, for ***now***, generic constraints for primitive "numbers"
public struct Point2D<TX, TY>
where TX : struct, IComparable, IFormattable, IConvertible, IComparable<TX>, IEquatable<TX>
where TY : struct, IComparable, IFormattable, IConvertible, IComparable<TY>, IEquatable<TY>
{
public static Point2D<TX, TY> Empty = new Point2D<TX, TY>();

public Point2D(TX x, TY y)
{
this._x = x;
this._y = y;
}

// C# 6 I miss you here: sad
private readonly TY _y;
public TY Y
{
get
{
return this._y;
}
}

// and there too :-(
private readonly TX _x;
public TX X
{
get
{
return this._x;
}
}
}
}

欢迎提出更多相关问题。

关于c# - MS Chart 中的插值实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13283118/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com