.interp.poly
author Andreas Thurnherr <ant@ldeo.columbia.edu>
Mon, 13 Apr 2020 11:06:22 -0400
changeset 40 c1803ae2540f
parent 39 56bdfe65a697
permissions -rw-r--r--
.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
39
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     1
#======================================================================
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     2
#                    . I N T E R P . P O L Y 
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     3
#                    doc: Thu Nov 23 21:30:25 2000
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     4
#                    dlm: Tue Aug  5 14:20:19 2008
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     5
#                    (c) 2000 A.M. Thurnherr
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     6
#                    uE-Info: 58 0 NIL 0 0 72 10 2 4 NIL ofnI
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     7
#======================================================================
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     8
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
     9
# polynomial interpolation
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    10
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    11
# HISTORY:
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    12
# 	Nov 23, 2000: - created
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    13
#	Nov 24, 2000: - added -c)enter x-val in window
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    14
#	Dec 13, 2002: - replaced -n by -o
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    15
#	Oct 22, 2003: - changed -e to -r (conflicts with -e option of [resample])
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    16
#	Jul 28, 2006: - removed debugging code
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    17
#				  - added xf to ISInit() args
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    18
#				  - BUG: sufficient-input data test was buggy
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    19
#   Aug 22, 2006: - adapted to work with [match]
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    20
#	Sep 11, 2006: - BUG: sufficient-input ermesg was wrong
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    21
#   Aug  5, 2008: - added idr param to IS_init()
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    22
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    23
# see [.interp.linear] for documentation of interface
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    24
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    25
# NOTES:
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    26
#	- $opt_o <poly order> is required
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    27
#	- $opt_r is used to return the error estimates instead of the
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    28
#	  interpolated values
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    29
#	- -o 0 is almost like using -s subsample, the only difference
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    30
#	  being that subsample returns the real x values while -o 0
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    31
#	  returns the subsampled x values
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    32
#	- on -c the window for each interpolation estimate is centered
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    33
#	  around the interpolated x value; this implies window-sliding
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    34
#	  between tabulated x values resulting in functional disconti-
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    35
#	  nuities
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    36
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    37
require	"$ANTS/polint.pl";
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    38
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    39
$IS_opts = "co:r";
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    40
$IS_optsUsage = "[e-r)ror estimates] [-c)enter x-val] -o <poly order>";
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    41
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    42
sub IS_usage()
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    43
{
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    44
	die("$0 (.interp.poly): ERROR! -o required\n")
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    45
		unless (defined($opt_o) && $opt_o >= 0);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    46
	&antsInfo("WARNING: -c generates discontinuous function")
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    47
		if ($opt_c);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    48
	&antsInfo("WARNING: high-order polynomial interpolation deprecated")
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    49
		if ($opt_o > 5);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    50
	&antsInfo("order-1 polynomial; -s linear is more efficient")
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    51
		if ($opt_o == 1);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    52
	&antsInfo("giving error estimates") if ($opt_r);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    53
}
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    54
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    55
sub IS_init($$$$)
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    56
{
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    57
	my($bR,$idR,$f,$xf) = @_;
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    58
	die(sprintf("$0 (.interp.poly): ERROR! " .
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    59
				"not enough data points (%d) for order-$opt_o poly\n",
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    60
				 $#{$bR}+1))
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    61
		if ($opt_o > $#{$bR});
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    62
}
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    63
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    64
sub findWindow($$$$$)							# find window of size n=opt_o+1
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    65
{
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    66
	my($bR,$f,$v,$i,$n) = @_;
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    67
	my($cn);									# current win size
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    68
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    69
	return ($bR->[$i+1][$f] - $v < $v - $bR->[$i][$f]) ? $i+1 : $i
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    70
		if ($n == 1);							# nearest neighbor
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    71
		
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    72
	if ($opt_c) {								# center window around x value
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    73
		for ($cn=2; $cn<$n; $cn++) {			# grow window
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    74
			$i-- if (($i>0 && $bR->[$i+$cn-1][$f] - $v >= $v - $bR->[$i][$f]) ||
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    75
					 ($i+$cn-1 == $#{$bR}));
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    76
		}
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    77
	} else {
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    78
		$i -= int(($n-1)/2);						# ideally
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    79
		$i  = 0 if ($i < 0);						# off leftmost column
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    80
		$i  = $#{$bR}+1 - $n if ($i+$n > $#{$bR}+1);# off rightmost column
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    81
	}
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    82
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    83
	return $i;
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    84
}
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    85
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    86
sub IS_interpolate($$$$$$)
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    87
{
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    88
	my($bR,$idR,$xf,$xv,$xi,$f) = @_;
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    89
	return $xv if ($xf == $f);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    90
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    91
	$xi = &findWindow($bR,$xf,$xv,$xi,$opt_o+1);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    92
	my($y,$dy) = &polint($bR,$xf,$xv,$xi,$opt_o+1,$f);
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    93
	return $opt_r ? $dy : $y;
A.M. Thurnherr <athurnherr@yahoo.com>
parents:
diff changeset
    94
}