Показывать сложный интерес в C#
Это более графическая версия примера Рассчитайте значение ежемесячной инвестиции в C# . Вместо добавления значений в элемент управления ListView этот пример сохраняет точки в трех списках точек: Balance, Contributions и Interest . Затем он отображает эти значения.
Следующий метод PerformCalculations показывает, как программа вычисляет и сохраняет эти значения.
// Точки данных. private ListContributions = new List (); private List Interest = new List (); private List Balance = new List (); // Выполните вычисления. private void PerformCalculations() { // Получить параметры. decimal monthly_contribution = decimal.Parse( txtMonthlyContribution.Text, NumberStyles.Any); int num_months = int.Parse(txtNumMonths.Text); decimal interest_rate = decimal.Parse( txtInterestRate.Text.Replace("%", "")) / 100; interest_rate /= 12; // Начало в 0. Contributions = new List (); Interest = new List (); Balance = new List (); decimal contributions = 0; decimal interest = 0; decimal balance = 0; // Вычислить. for (int i = 0; i <= num_months; i++) { // Сохранение вкладов, процентов и баланса. Contributions.Add(new PointF(i, (float)contributions)); Interest.Add(new PointF(i, (float)interest)); Balance.Add(new PointF(i, (float)balance)); // Вычислить значения для следующего месяца. contributions += monthly_contribution; decimal new_interest = balance * interest_rate; interest += new_interest; balance += monthly_contribution + new_interest; } // Добавить точки, чтобы закрыть многоугольники. Contributions.Add(new PointF(num_months, 0)); Interest.Add(new PointF(num_months, 0)); Balance.Add(new PointF(num_months, 0)); // Перерисовать. picGraph.Refresh(); }
Большая часть этого метода проста. Он просто добавляет новые точки данных, представляющие текущие взносы учетной записи, баланс и проценты. Затем он добавляет ежемесячный взнос в общий объем взносов, рассчитывает проценты за месяц и обновляет баланс в течение следующего месяца.
Конец метода добавляет еще один пункт в каждый список. Точка имеет ту же самую координату X, что и конечная точка данных (координата X представляет месяц) и координата Y 0 (представляющая $ 0). Это приводит к тому, что последовательность точек возвращается к оси X, поэтому программа может заполнять их как многоугольник, как показано на рисунке.
Следующий код показывает, как программа рисует график.
// Преобразование чертежа. private Matrix Transform; // Рисуем график. private void picGraph_Paint(object sender, PaintEventArgs e) { e.Graphics.Clear(picGraph.BackColor); if (Balance.Count < 2) return; e.Graphics.SmoothingMode = SmoothingMode.AntiAlias; // Масштабируем, чтобы данные соответствовали. float xmin = -1; float xmax = Contributions.Count + 1; float ymax = Balance.Max(pt => pt.Y); float ymin = -ymax * 0.05f; RectangleF rect = new RectangleF(xmin, ymin, xmax - xmin, ymax - ymin); PointF[] pts = { new PointF(0, picGraph.ClientSize.Height), new PointF( picGraph.ClientSize.Width, picGraph.ClientSize.Height), new PointF(0, 0), }; Transform = new Matrix(rect, pts); e.Graphics.Transform = Transform; // Рисуем кривые. e.Graphics.FillPolygon(Brushes.LightGreen, Balance.ToArray()); e.Graphics.FillPolygon(Brushes.LightBlue, Contributions.ToArray()); e.Graphics.FillPolygon(Brushes.Pink, Interest.ToArray()); e.Graphics.DrawPolygon(Pens.Green, Balance.ToArray()); e.Graphics.DrawPolygon(Pens.Blue, Contributions.ToArray()); e.Graphics.DrawPolygon(Pens.Red, Interest.ToArray()); }
Обработчик события Paint создает преобразование для сопоставления данных на picGraph PictureBox. Он сохраняет преобразование в переменной Transform для последующего использования.
Затем метод заполняет три кривые, а затем очерчивает их.
Последняя интересная часть программы - это следующий код, который заставляет программу отображать значения данных во всплывающей подсказке при перемещении мыши по графику.
// Отображение значений ближайшей точки данных. private const float max_dx = 5; private void picGraph_MouseMove(object sender, MouseEventArgs e) { if (Balance.Count < 3) return; // Найдите точку данных, ближайшую к мыши. string tip = ""; if (tip == "") tip = GetDataTooltip(Balance, e.Location, "Balance"); if (tip == "") tip = GetDataTooltip(Contributions, e.Location, "Contributions"); if (tip == "") tip = GetDataTooltip(Interest, e.Location, "Interest"); // Отобразите новый подсказку. if (tip != tipAmount.GetToolTip(picGraph)) { tipAmount.SetToolTip(picGraph, tip); Console.WriteLine("[" + tip + "]"); } }
Обработчик события MouseMove вызывает метод GetDataTooltip три раза, один раз для каждого набора данных. Если новый текст всплывающей подсказки, возвращаемый этим методом, отличается от того, который в настоящее время отображается picGraph PictureBox, тогда программа устанавливает всплывающую подсказку элемента управления в новое значение. (Если вы установите новую всплывающую подсказку, не проверяя, изменилась ли она, тогда всплывающая подсказка мерцает. Удалите тест if, чтобы увидеть это.)
В следующем коде показан метод GetDataTooltip.
// Найдите подсказку для данных точек данных. private string GetDataTooltip(Listpoint_list, Point location, string type_name) { const float max_dist = 6; // Преобразуем точки в координаты экрана. PointF[] points = point_list.ToArray(); Transform.TransformPoints(points); // Смотрите, находится ли какая-либо из точек близко к местоположению, // пропускаем последнюю точку, которая использовалась для закрытия многоугольника. for (int i = 0; i < point_list.Count - 1; i++) { // Посмотрим, достаточно ли эта точка для мыши. float dist = Math.Abs(points[i].X - location.X) + Math.Abs(points[i].Y - location.Y); if (dist < max_dist) { return "Month: " + point_list[i].X.ToString() + "\n" + type_name + ": " + point_list[i].Y.ToString("C"); } } return ""; }
Этот метод преобразует список точек данных в массив. Затем он использует преобразование чертежа, чтобы преобразовать их, как если бы они рисовали их. Это ставит точки и местоположение мыши в одну и ту же систему координат экрана.
Далее метод проходит через точки. Если он найдет точку, которая достаточно близка к местоположению мыши, метод составляет соответствующее сообщение всплывающей подсказки и возвращает его.
Вы можете видеть на картинке, что кривая процента становится все круче. Если вы продлеваете тест до 240 месяцев или около того, кривая процента растет достаточно круто, чтобы превышать взносы.