2 * linear least squares model
4 * Copyright (c) 2006 Michael Niedermayer <michaelni@gmx.at>
6 * This file is part of FFmpeg.
8 * FFmpeg is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * FFmpeg is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with FFmpeg; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
25 * linear least squares model
32 #include "attributes.h"
35 static void update_lls(LLSModel
*m
, const double *var
)
39 for (i
= 0; i
<= m
->indep_count
; i
++) {
40 for (j
= i
; j
<= m
->indep_count
; j
++) {
41 m
->covariance
[i
][j
] += var
[i
] * var
[j
];
46 void avpriv_solve_lls(LLSModel
*m
, double threshold
, unsigned short min_order
)
49 double (*factor
)[MAX_VARS_ALIGN
] = (void *) &m
->covariance
[1][0];
50 double (*covar
) [MAX_VARS_ALIGN
] = (void *) &m
->covariance
[1][1];
51 double *covar_y
= m
->covariance
[0];
52 int count
= m
->indep_count
;
54 for (i
= 0; i
< count
; i
++) {
55 for (j
= i
; j
< count
; j
++) {
56 double sum
= covar
[i
][j
];
58 for (k
= 0; k
<= i
-1; k
++)
59 sum
-= factor
[i
][k
] * factor
[j
][k
];
64 factor
[i
][i
] = sqrt(sum
);
66 factor
[j
][i
] = sum
/ factor
[i
][i
];
71 for (i
= 0; i
< count
; i
++) {
72 double sum
= covar_y
[i
+ 1];
74 for (k
= 0; k
<= i
-1; k
++)
75 sum
-= factor
[i
][k
] * m
->coeff
[0][k
];
77 m
->coeff
[0][i
] = sum
/ factor
[i
][i
];
80 for (j
= count
- 1; j
>= min_order
; j
--) {
81 for (i
= j
; i
>= 0; i
--) {
82 double sum
= m
->coeff
[0][i
];
84 for (k
= i
+ 1; k
<= j
; k
++)
85 sum
-= factor
[k
][i
] * m
->coeff
[j
][k
];
87 m
->coeff
[j
][i
] = sum
/ factor
[i
][i
];
90 m
->variance
[j
] = covar_y
[0];
92 for (i
= 0; i
<= j
; i
++) {
93 double sum
= m
->coeff
[j
][i
] * covar
[i
][i
] - 2 * covar_y
[i
+ 1];
95 for (k
= 0; k
< i
; k
++)
96 sum
+= 2 * m
->coeff
[j
][k
] * covar
[k
][i
];
98 m
->variance
[j
] += m
->coeff
[j
][i
] * sum
;
103 static double evaluate_lls(LLSModel
*m
, const double *param
, int order
)
108 for (i
= 0; i
<= order
; i
++)
109 out
+= param
[i
] * m
->coeff
[order
][i
];
114 av_cold
void avpriv_init_lls(LLSModel
*m
, int indep_count
)
116 memset(m
, 0, sizeof(LLSModel
));
117 m
->indep_count
= indep_count
;
118 m
->update_lls
= update_lls
;
119 m
->evaluate_lls
= evaluate_lls
;