Dipatch on AbstractArray which contains missing values

I have a Vector:

a_vec=[missing, 1, 2, 3]

When I need to calculate the mean of a_vec, I used to do:

mean(skipmissing(a_vec))
2

This is the most situation I met. So I would like to skipmissing by default, I would like to do:

Base.mean(x) = mean(skipmissing(x))

But the skipmissing call consume time, So I have to do:

Base.mean(x::AbstractArray{T,1}) where {Missing <: T}=mean(skipmissing(x))

UndefVarError: T not defined

In another way, I could do it by:

Base.mean(x::AbstractArray{T,1}) where {T<:Number,1}=mean(x)
Base.mean(x)=mean(skipmissing(x))

But when I use sum, var etc…, have to do it again and again.

So what should I do to dispath method on AbstractArray containing missing?

Two side notes (I’m on a mobile): first the “call” itself to skipmissing is likelly to be negligible compared with the rest of your operations, and secondly what you are trying to do (override a method for a type you don’t own) is considered very bad practice and goes under the name of “type piracy”.
Think if you write a package that override Base.mean and then someone use your package .
Then when he/she compute the mean for even unrelated things he/she will have the modified behaviour without knowing it!

2 Likes

In addtion to sylvaticus’ very important points, I have two comments

  1. The stats functions like mean etc. are not in Base but in Statistics
  2. The T in your dispatch should be Union{Missing, T}

But IMHO it’s really much simpler and clearer to be explicit about it at the expense of a few extra characters

import Base: skipmissing as sm
mean(sm([missing,1])) = 1.0
1 Like

It shouldn’t make any difference whether you call mean(skipmissing(x)) or change the definition of mean itself, like you are trying. It still calls skipmissing.

BTW, this definition is recursive.

1 Like

Thank you for your reply and advice. Acturelly, in my local code, the code seems like

Statistics.quantile(x::AA{U{Mi,T},1},y) where {T}=quantile(smiss(x),y)
#=
const  AA = AbstractArray
const Mi = Missing
const U = Union
=#