Category Archives: Julia

From Simulation to Hardware: JuliaHub’s End-to-End Workflow for Embedded Control Systems

By: JuliaHub

Re-posted from: https://info.juliahub.com/blog/juliahubs-end-to-end-workflow

Designing embedded control systems typically involves a fragmented workflow—engineers model and simulate control logic in one environment, while developers manually rewrite and deploy that logic in another. This “two-culture problem” slows down development, introduces errors, and makes iteration costly.

How to Tune a Kalman Filter: Step-by-Step Guide | JuliaHub

By: Fredrik Bagge Carlson

Re-posted from: https://info.juliahub.com/blog/tune-kalman-filter

The celebrated Kalman filter finds applications in many fields of engineering and economics. While many are familiar with the basic concepts of the Kalman filter, almost equally many find the “tuning parameters” associated with a Kalman filter nonintuitive and difficult to choose. While there are several parameters that can be tuned in a real-world application of a Kalman filter, we will focus on the most important ones: the process and measurement noise covariance matrices.

The Kalman filter

The Kalman filter is a form of Bayesian estimation algorithm that estimates the state $$x$$ of a linear dynamical system, subject to Gaussian noise $$e$$ acting on the measurements as well as the dynamics, $$w$$. More precisely, let the dynamics of a discrete-time linear dynamical system be given by

$$x_{k+1} = {Ax_k + Bu_k + w_k}$$
$$y_k = {Cx_k + Du_k + e_k}$$

 

where $$x_k \in \Bbb R^{n_x}$$ is the state of the system at time $$k, u_k \in \Bbb R^{n_u}$$ is an external input, $$A$$ and $$B$$ are the state transition and input matrices respectively, $$c$$ an output matrix and $$w_k \backsim N(0, R_1) $$ and $$e_k \backsim N(0, R_1) $$, are normally distributed process noise and measurement noise terms respectively. A state estimator like the Kalman filter allows us to estimate $$x$$ given only noisy measurements $$y \in \Bbb R^{n_y}$$, i.e., without necessarily having measurements of all the components of $$x$$ available.[obs] For this reason, state estimators are sometimes referred to as virtual sensors, i.e., they allows use to estimate what we cannot measure.

The Kalman filter is popular for several important reasons, for one, it is the optimal estimator in the mean-square sense if the system dynamics is linear (can be time varying) and the noise acting on the system is Gaussian. In most practical applications, neither of these conditions hold exactly, but they often hold sufficiently well for the Kalman filter to remain useful.[nonlin] A perhaps even more useful property of the Kalman filter is that the posterior probability distribution over the state remains Gaussian throughout the operation of the filter, making it efficient to compute and store.

obs: Under a technical condition on the observability of the system dynamics.

nonlin: Several nonlinear state estimators exist as well.

What does “tuning the Kalman filter” mean?

To make use of a Kalman filter, we obviously need the dynamical model of the system given by the four matrices $$A,B,C$$ and $$D$$. We furthermore require a choice of the covariance matrices $$R_1$$ and $$R_2$$, and it is here a lot of aspiring Kalman-filter users get stuck. The covariance matrix of the measurement noise is often rather straightforward to estimate, just collect some measurement data when the system is at rest and compute the sample covariance, but we often lack any and all feeling for what the process noise covariance, $$R_1$$, should be.

In this blog post, we will try to give some intuition for how to choose the process noise covariance matrix $$R_1$$. We will come at this problem from a disturbance-modeling perspective, i.e., trying to reason about what disturbances act on the system and how, and what those imply for the structure and value of the covariance matrix $$R_1$$.

CUDA.jl 5.8: CuSparseVector broadcasting, CUDA 12.9, and more

By: Tim Besard

Re-posted from: https://juliagpu.org/post/2025-05-14-cuda_5.8/index.html

CUDA.jl v5.8 brings several enhancements, most notably the introduction of broadcasting support for CuSparseVector. The release also includes support for CUDA 12.9, and updates to key CUDA libraries like cuTENSOR, cuQuantum, and cuDNN.

Broadcasting for CuSparseVector

A significant enhancement in CUDA.jl v5.8 is the support for broadcasting CuSparseVector. Thanks to @kshyatt, it is now possible to use sparse GPU vectors in broadcast expressions just like it was already possible with sparse matrices:

julia> using CUDA, .CUSPARSE, SparseArraysjulia> x = cu(sprand(Float32, 10, 0.3))
10-element CuSparseVector{Float32, Int32} with 4 stored entries:
  [2]  =  0.459139
  [3]  =  0.964073
  [8]  =  0.904363
  [9]  =  0.721723julia> # a zero-preserving elementwise operation
       x .* 2
10-element CuSparseVector{Float32, Int32} with 4 stored entries:
  [2]  =  0.918278
  [3]  =  1.928146
  [8]  =  1.808726
  [9]  =  1.443446julia> # a non-zero-preserving elementwise operation
       x .+ 1
10-element CuArray{Float32, 1, CUDA.DeviceMemory}:
 1.0
 1.4591388
 1.9640732
 1.0
 1.0
 1.0
 1.0
 1.9043632
 1.7217231
 1.0julia> # combining multiple sparse inputs
       x .+ cu(sprand(Float32, 10, 0.3))
10-element CuSparseVector{Float32, Int32} with 6 stored entries:
  [1]  =  0.906
  [2]  =  0.583197
  [3]  =  0.964073
  [4]  =  0.259103
  [8]  =  0.904363
  [9]  =  0.935917

Minor Changes

CUDA.jl 5.8 also includes several other useful updates:

As always, we encourage users to update to the latest version to benefit from these improvements and bug fixes. Check out the changelog for a full list of changes.