How to get Simplified variance of a random variable?

Hi all,

I want to use Julia to get the end result like this:
Capture d’écran_2023-02-23_17-57-29

the Expectation of (X - \mu)^{2} will be computed at the end to become:

E(X^{2}) - \mu^{2}

but how?

this is my try out:

using SymPy
@syms x, μ

v = expand((x-μ)^2)

function E(h)
	if h == x^2
	  return x^2
	elseif h==x*μ
	  return x*μ
	elseif h==μ^2
	  return μ^2

what should I do next? I was thinking of creating a function with if and ifelse, maybe there is another way?

Not sure if I understand what you want to do in the end:

  • Compute the variance of a random variable based on a sample? If you have a sample of the random variable X and want to know/estimate the variance, there would be tools for that in Statistics · The Julia Language And probably lots more.
  • Compute the variance based on its distribution? Then perhaps Distributions Package · Distributions.jl is more useful.
  • (I guess this is what you want) Represent random variables symbolically in a program? E.g. the operation \mathbb{E} which represents the mean of a random variable with the properties you described (e.g. \mathbb{E}(\mathbb{E}(X)) = \mathbb{E}(X) ). I’m not sure if there is a package that does this already, but it seems like sympy does have types that represent random variables – doesn’t seem like they have been ported to SymPy.jl yet though.

Here is an overview of what sympy can do

If you just want to implement a “rewriting rule” that takes an expression like E((x - mu)^2) and returns E(x^2) - mu^2 this might also be helpful: SymbolicUtils.jl

Perhaps you could define a symbolic function E and specify some rewrite rules.


Yes! I want to implement “rewriting rule”

but the SymbolicUtils package does not work, I tried it:
Capture d’écran_2023-02-23_22-03-34

Anyway, I want to try SymPy, thanks for pointing out it is rewriting technique… I just need to know the method or name.

In Probability and Statistics there are tons of this to prove E(X^{2}), etc…

I try to use PyCall and SymPy:

using PyCall

ENV["PYTHON"] = "/home/browni/.julia/conda/3/bin/python3"
# the path is from the command 'which python3'

from sympy import symbols, Integral
from sympy.stats import Normal, Expectation, Variance, Probability

mu = symbols("μ", positive=True)

sigma = symbols("σ", positive=True)

#pdf = (15/512)*(x**2)*((4-x)**2)
X = Normal("X", mu, sigma)

print('Normal distribution')
print('Var(X) =',Variance(X).evaluate_integral())

print('E(X-μ) =',Expectation((X - mu)**2).expand())
print('final computation:')
print('E(X-μ) =',Expectation((X - mu)**2).doit())


Just to add to this excellent answer, you may need to import the stats module to use within SymPy.jl. Here are steps that should work for that:

import PyCall
PyCall.pyimport_conda("sympy.stats", "sympy")

Here is a sample usage:

Z = sympy.stats.Normal("Z", 0, 1)
sympy.stats.E((Z- 0)^2)

It should work. Did you start a new REPL session when trying the code?
Both SymPy.jl and SymbolicUtils.jl export @syms, so what happened in your case is probably that z is a Sympy symbol and thus the rewriting does not work (it looks for SymbolicUtils symbols in the expression).

1 Like

it works after restarting REPL. Intersecting with SymPy is the problem. Thanks!

1 Like