Fitting for experimental data
this experiment, we are going to explore another built-in
function in Scilab intended for curve fitting or finding parameters or
coefficients. Its name is ‘datafit’.
Naturally, you can see all the
possibilities and uses of the function if you type “help datafit”
command window. The online reference manual should always be your first
We are going to use the
simplest case for fitting a curve to
given or found data.
Let’s say that we have
collected some results from an
experiment. These are the specific numbers
If we graph the table in
Scilab, we’re going to get this
Now, let’s say that we
know in advance that those measured
or somehow collected points in our experiment are part of a nonlinear
of this type:
Our mission is to find
the parameters C1, C2
We know that the function
datafit is used for fitting data
to a model. For a given function G(p, z), this function finds the best
of parameters p for approximating G(p, zi) = 0
for a set of
measurement vectors zi. Vector p is found by
minimizing G(p, z1)'
WG(p, z1) + G(p, z2)'
WG(p, z2) + ... + G(p, zn)'
- G is a
- W is a
datafit is an improved
version of fit_dat, also available in
The first step in our
demonstration is to create a file
that includes our parameterized function (in this case
and our way to measure the error (in this case the function
is called myerror).
This is one way to do
// This function takes vector x and the
// of the function
function y = data_fit_1(x, c)
cos(c(2)*x) + c(3)*sin(x);
// This is a way to measure the error, to
find the least one.
// The error function will call the parameterized function.
function e = myerror(c, z)
z(1); y = z(2);
e = y
Now, we can create a main
script that can use the function
datafit and the input data. One way to do it is like this:
// Clear windows, memory and screen
xdel(winsid()); clear; clc
// Load our functions into memory
// Measured data in vectors x and y
x = [0 0.55 1.11 1.66 2.22 ...
2.77 3.33 3.88
y = [1 0.47 3.73 2.22 2.61 ...
1.63 -2.13 0.62
// Plot the original data
plot(x, y, 'ro')
// Prepare vector z with given coordinates
z = [x; y];
// This is our first attempt to find the parameters
c0 = [2 2 2]';
// copt is supposed to be the best result
// err is the value of the error at the end of the process
[copt, err] = datafit(myerror, z, c0);
// Let's see how good our
linspace(0, 5, 100);
This is the
err = 43.654725
It was a nice try, but
the error was very high (it should be close to zero) and our result was
not good at all.
We could manually try
different values in c0,
point. We can expect Scilab to deliver different results if we enter
seeds as starting points...
Let’s try a different
approach. We’re going to create a loop
of 10 iterations. We can create a random vector for c0 (the seed)
each time, and we are
going to take the best result after those 10 attempts. It’s another way
approaching the problem, instead of going one vector at a time...
I can suggest something
similar to this code...
// Let’s try random starting seeds between
-5 and 5
a = -5; b = 5;
for k = 1 : 10
c0 = a
+ (b -
= datafit(myerror, z, c0);
// The least error after 10 trials is
[m, k] = min(err)
copt = copt(:,k)
// Let’s plot the best found
linspace(0, 5, 100);
And we get this result...
k = 3
Much better..., now our
function has an error of only 0.003
(found in the third iteration) and the best found coefficients produce
function that hits the experimental data almost perfectly.
Maybe you're interested in
'Curve Fit' to Matlab home
'Curve Fit' to Scilab examples