public static void triangle() //****************************************************************************80 // // Purpose: // // MAIN is the main program for TRIANGLE. // // Discussion: // // This driver computes the interpolation of the Franke function // on the triangle T(U,V,W) with vertices U=(U1,U2)=(0,0), // V=(V1,V2)=(1,0) and W=(W1,W2)=(0,1) (unit triangle) // at the first family of Padua points. // // The degree of interpolation is DEG = 60 and the number of target // points is NTG = NTG1 ** 2 - NTG1 + 1, NTG1 = 100. // // The maps from the reference square [-1,1]^2 to the triangle // are SIGMA1 and SIGMA2 with inverses ISIGM1 and ISIGM2. // // Licensing: // // This code is distributed under the GNU LGPL license. // // Modified: // // 16 February 2014 // // Author: // // Original FORTRAN77 version by Marco Caliari, Stefano De Marchi, // Marco Vianello. // This C version by John Burkardt. // // Reference: // // Marco Caliari, Stefano de Marchi, Marco Vianello, // Algorithm 886: // Padua2D: Lagrange Interpolation at Padua Points on Bivariate Domains, // ACM Transactions on Mathematical Software, // Volume 35, Number 3, October 2008, Article 21, 11 pages. // // Parameters: // // Local, int DEGMAX, the maximum degree of interpolation. // // Local, int NPDMAX, the maximum number of Padua points // = (DEGMAX + 1) * (DEGMAX + 2) / 2. // // Local, int NTG1MX, the maximum value of the parameter determining // the number of target points. // // Local, int NTGMAX, the maximum number of target points, // dependent on NTG1MX. // // Local, int DEG, the degree of interpolation. // // Local, int NTG1, the parameter determining the number // of target points. // // Local, int NPD, the number of Padua points = (DEG + 1) * (DEG + 2) / 2. // // Local, int NTG, the number of target points, dependent on NTG1. // // Local, double PD1(NPDMAX), the first coordinates of // the Padua points. // // Local, double PD2(NPDMAX), the second coordinates of the // Padua points. // // Local, double WPD(NPDMAX), the weights. // // Local, double FPD(NPDMAX), the function at the Padua points. // // Workspace, double RAUX1(DEGMAX+1)*(DEGMAX+2)). // // Workspace, double RAUX2(DEGMAX+1)*(DEGMAX+2)). // // Local, double C0(0:DEGMAX+1,0:DEGMAX+1), the coefficient matrix. // // Local, double TG1(NTGMAX), the first coordinates of the // target points. // // Local, double TG2(NTGMAX), the second coordinates of the // target points. // // Local, double INTFTG(NTGMAX), the values of the // interpolated function. // // Local, double MAXERR, the maximum norm of the error at target // points. // // Local, double ESTERR, the estimated error. // { const int DEGMAX = 60; const int NTG1MX = 100; const int NPDMAX = (DEGMAX + 1) * (DEGMAX + 2) / 2; const int NTGMAX = NTG1MX * NTG1MX - NTG1MX + 1; double[] c0 = new double[(DEGMAX + 2) * (DEGMAX + 2)]; double esterr = 0; double[] fpd = new double[NPDMAX]; int i; double[] intftg = new double[NTGMAX]; double maxdev; int npd = 0; int ntg = 0; List <string> output = new(); double[] pd1 = new double[NPDMAX]; double[] pd2 = new double[NPDMAX]; double[] raux1 = new double[(DEGMAX + 1) * (DEGMAX + 2)]; double[] raux2 = new double[(DEGMAX + 1) * (DEGMAX + 2)]; double[] tg1 = new double[NTGMAX]; double[] tg2 = new double[NTGMAX]; double[] wpd = new double[NPDMAX]; double x; double y; const double u1 = 0.0; const double u2 = 0.0; const double v1 = 1.0; const double v2 = 0.0; const double w1 = 0.0; const double w2 = 1.0; const int deg = 60; const int ntg1 = 100; Console.WriteLine(""); Console.WriteLine("TRIANGLE:"); Console.WriteLine(" Interpolation of the Franke function"); Console.WriteLine(" on the unit triangle T((0,0),(1,0),(0,1))"); Console.WriteLine(" at degree = " + deg + ""); // // Build the first family of Padua points in the square [-1,1]^2 // Padua.pdpts(deg, ref pd1, ref pd2, ref wpd, ref npd); // // Compute the Franke function at Padua points mapped to T(U,V,W). // for (i = 0; i < npd; i++) { x = sigma1(pd1[i], pd2[i], u1, u2, v1, v2, w1, w2); y = sigma2(pd1[i], pd2[i], u1, u2, v1, v2, w1, w2); fpd[i] = Franke.franke(x, y); } // // Write X, Y, F(X,Y) to a file. // string filename = "triangle_fpd.txt"; for (i = 0; i < npd; i++) { x = sigma1(pd1[i], pd2[i], u1, u2, v1, v2, w1, w2); y = sigma2(pd1[i], pd2[i], u1, u2, v1, v2, w1, w2); output.Add(x + " " + y + " " + fpd[i] + ""); } File.WriteAllLines(filename, output); Console.WriteLine(""); Console.WriteLine(" Wrote F(x,y) at Padua points in '" + filename + "'"); // // Compute the matrix C0 of the coefficients in the bivariate // orthonormal Chebyshev basis // Padua.padua2(deg, DEGMAX, npd, wpd, fpd, raux1, raux2, ref c0, ref esterr); // // Build the set of target points on T(U,V,W) // target(u1, u2, v1, v2, w1, w2, ntg1, NTGMAX, ref tg1, ref tg2, ref ntg); // // Evaluate the interpolant at the target points. // for (i = 0; i < ntg; i++) { x = isigm1(tg1[i], tg2[i], u1, u2, v1, v2, w1, w2); y = isigm2(tg1[i], tg2[i], u1, u2, v1, v2, w1, w2); intftg[i] = Padua.pd2val(deg, DEGMAX, c0, x, y); } // // Write the function value at target points to a file. // filename = "triangle_ftg.txt"; for (i = 0; i < ntg; i++) { output.Add(tg1[i] + " " + tg2[i] + " " + Franke.franke(tg1[i], tg2[i]) + ""); } File.WriteAllLines(filename, output); Console.WriteLine(" Wrote F(x,y) at target points in '" + filename + "'"); // // Write the interpolated function value at target points to a file. // filename = "triangle_itg.txt"; for (i = 0; i < ntg; i++) { output.Add(tg1[i] + " " + tg2[i] + " " + intftg[i] + ""); } File.WriteAllLines(filename, output); Console.WriteLine(" Wrote I(F)(x,y) at target points in '" + filename + "'"); // // Compute the error relative to the max deviation from the mean. // double maxerr = 0.0; double mean = 0.0; double fmax = -typeMethods.r8_huge(); double fmin = +typeMethods.r8_huge(); for (i = 0; i < ntg; i++) { double fxy = Franke.franke(tg1[i], tg2[i]); double ixy = intftg[i]; maxerr = Math.Max(maxerr, Math.Abs(fxy - ixy)); mean += fxy; fmax = Math.Max(fmax, fxy); fmin = Math.Min(fmin, fxy); } if (Math.Abs(fmax - fmin) <= double.Epsilon) { maxdev = 1.0; } else { mean /= ntg; maxdev = Math.Max(fmax - mean, mean - fmin); } // // Print error ratios. // Console.WriteLine(""); Console.WriteLine(" Estimated error: " + esterr / maxdev + ""); Console.WriteLine(" Actual error: " + maxerr / maxdev + ""); Console.WriteLine(" Expected error: " + 0.1226E-09 + ""); // // Terminate. // Console.WriteLine(""); Console.WriteLine("TRIANGLE:"); Console.WriteLine(" Normal end of execution."); Console.WriteLine(""); }
public static void ellipse() //****************************************************************************80 // // Purpose: // // MAIN is the main program for ELLIPSE. // // Discussion: // // This driver computes the interpolation of the Franke function // on the ellipse E((C1,C2),ALPHA,BETA) = E((0.5,0.5),0.5,0.5) // at the first family of Padua points. // // The ellipse has the equation: // // ( ( X - C1 ) / ALPHA )^2 + ( ( Y - C2 ) / BETA )^2 = 1 // // The degree of interpolation DEG = 60 and the number of target // points is NTG = NTG1 ^ 2 - 2 * NTG1 + 2, NTG1 = 100. // // The maps from the reference square [-1,1]^2 to the current domain // are SIGMA1 and SIGMA2 with inverses ISIGM1 and ISIGM2. // // Licensing: // // This code is distributed under the GNU LGPL license. // // Modified: // // 16 February 2014 // // Author: // // Original FORTRAN77 version by Marco Caliari, Stefano De Marchi, // Marco Vianello. // C++ version by John Burkardt. // // Reference: // // Marco Caliari, Stefano de Marchi, Marco Vianello, // Algorithm 886: // Padua2D: Lagrange Interpolation at Padua Points on Bivariate Domains, // ACM Transactions on Mathematical Software, // Volume 35, Number 3, October 2008, Article 21, 11 pages. // // Local Parameters: // // Local, int DEGMAX, the maximum degree of interpolation. // // Local, int NPDMAX, the maximum number of Padua points // = (DEGMAX + 1) * (DEGMAX + 2) / 2. // // Local, int NTG1MX, the maximum value of the parameter determining // the number of target points. // // Local, int NTGMAX, the maximum number of target points, // dependent on NTG1MX. // // Local, int DEG, the degree of interpolation. // // Local, int NTG1, the parameter determining the number of target points. // // Local, int NPD, the number of Padua points = (DEG + 1) * (DEG + 2) / 2. // // Local, int NTG, the number of target points, dependent on NTG1. // // Local, double PD1[NPDMAX], the first coordinates of // the Padua points. // // Local, double PD2[NPDMAX], the second coordinates of the // Padua points. // // Local, double WPD[NPDMAX], the weights. // // Local, double FPD[NPDMAX], the function at the Padua points. // // Workspace, double RAUX1[(DEGMAX+1)*(DEGMAX+2)]. // // Workspace, double RAUX2[(DEGMAX+1)*(DEGMAX+2)]. // // Local, double C0[(0:DEGMAX+1)*(0:DEGMAX+1)], the coefficient matrix. // // Local, double TG1[NTGMAX], the first coordinates of the // target points. // // Local, double TG2[NTGMAX], the second coordinates of the // target points. // // Local, double INTFTG[NTGMAX], the values of the // interpolated function. // // Local, double MAXERR, the maximum norm of the error at target // points. // // Local, double ESTERR, the estimated error. // { const int DEGMAX = 60; const int NTG1MX = 100; const int NPDMAX = (DEGMAX + 1) * (DEGMAX + 2) / 2; const int NTGMAX = NTG1MX * NTG1MX - 2 * NTG1MX + 2; double[] c0 = new double[(DEGMAX + 2) * (DEGMAX + 2)]; double esterr = 0; double[] fpd = new double[NPDMAX]; int i; double[] intftg = new double[NTGMAX]; double maxdev; int npd = 0; int ntg = 0; List <string> output = new(); double[] pd1 = new double[NPDMAX]; double[] pd2 = new double[NPDMAX]; double[] raux1 = new double[(DEGMAX + 1) * (DEGMAX + 2)]; double[] raux2 = new double[(DEGMAX + 1) * (DEGMAX + 2)]; double[] tg1 = new double[NTGMAX]; double[] tg2 = new double[NTGMAX]; double[] wpd = new double[NPDMAX]; double x; double y; const double alpha = 0.5; const double beta = 0.5; const double c1 = 0.5; const double c2 = 0.5; const int deg = 60; const int ntg1 = 100; Console.WriteLine(""); Console.WriteLine("ELLIPSE:"); Console.WriteLine(" Interpolation of the Franke function"); Console.WriteLine(" on the disk with center = (0.5,0.5) and radius = 0.5"); Console.WriteLine(" of degree = " + deg + ""); // // Build the first family of Padua points in the square [-1,1]^2. // Padua.pdpts(deg, ref pd1, ref pd2, ref wpd, ref npd); // // Compute the Franke function at Padua points mapped to the region. // for (i = 0; i < npd; i++) { x = sigma1(pd1[i], pd2[i], c1, c2, alpha, beta); y = sigma2(pd1[i], pd2[i], c1, c2, alpha, beta); fpd[i] = Franke.franke(x, y); } // // Write X, Y, F(X,Y) to a file. // string filename = "ellipse_fpd.txt"; for (i = 0; i < npd; i++) { x = sigma1(pd1[i], pd2[i], c1, c2, alpha, beta); y = sigma2(pd1[i], pd2[i], c1, c2, alpha, beta); output.Add(x + " " + y + " " + fpd[i] + ""); } File.WriteAllLines(filename, output); Console.WriteLine(""); Console.WriteLine(" Wrote F(x,y) at Padua points in '" + filename + "'"); // // Compute the matrix C0 of the coefficients in the bivariate // orthonormal Chebyshev basis. // Padua.padua2(deg, DEGMAX, npd, wpd, fpd, raux1, raux2, ref c0, ref esterr); // // Evaluate the target points in the region. // target(c1, c2, alpha, beta, ntg1, NTGMAX, ref tg1, ref tg2, ref ntg); // // Evaluate the interpolant at the target points. // for (i = 0; i < ntg; i++) { x = isigm1(tg1[i], tg2[i], c1, c2, alpha, beta); y = isigm2(tg1[i], tg2[i], c1, c2, alpha, beta); intftg[i] = Padua.pd2val(deg, DEGMAX, c0, x, y); } // // Write the function value at target points to a file. // output.Clear(); filename = "ellipse_ftg.txt"; for (i = 0; i < ntg; i++) { output.Add(tg1[i] + " " + tg2[i] + " " + Franke.franke(tg1[i], tg2[i]) + ""); } File.WriteAllLines(filename, output); Console.WriteLine(" Wrote F(x,y) at target points in '" + filename + "'"); // // Write the interpolated function value at target points to a file. // output.Clear(); filename = "ellipse_itg.txt"; for (i = 0; i < ntg; i++) { output.Add(tg1[i] + " " + tg2[i] + " " + intftg[i] + ""); } File.WriteAllLines(filename, output); Console.WriteLine(" Wrote I(F)(x,y) at target points in '" + filename + "'"); // // Compute the error relative to the max deviation from the mean. // double maxerr = 0.0; double mean = 0.0; double fmax = -typeMethods.r8_huge(); double fmin = +typeMethods.r8_huge(); for (i = 0; i < ntg; i++) { double fxy = Franke.franke(tg1[i], tg2[i]); double ixy = intftg[i]; maxerr = Math.Max(maxerr, Math.Abs(fxy - ixy)); mean += fxy; fmax = Math.Max(fmax, fxy); fmin = Math.Min(fmin, fxy); } if (Math.Abs(fmax - fmin) <= double.Epsilon) { maxdev = 1.0; } else { mean /= ntg; maxdev = Math.Max(fmax - mean, mean - fmin); } // // Print error ratios. // Console.WriteLine(""); Console.WriteLine(" Estimated error: " + esterr / maxdev + ""); Console.WriteLine(" Actual error: " + maxerr / maxdev + ""); Console.WriteLine(" Expected error: " + 0.1769E-09 + ""); // // Terminate. // Console.WriteLine(""); Console.WriteLine("ELLIPSE:"); Console.WriteLine(" Normal end of execution."); Console.WriteLine(""); }