Transformation pour augmenter le kurtosis et l'asymétrie du rv normal

20

Je travaille sur un algorithme qui repose sur le fait que les observations sont normalement distribuées, et je voudrais tester empiriquement la robustesse de l'algorithme à cette hypothèse.Oui

Pour ce faire, je cherchais une suite de transformations qui perturberait progressivement la normalité de . Par exemple, si les sont normaux, ils ont une asymétrie et une kurtosis , et il serait bien de trouver une séquence de transformation qui augmente progressivement les deux.T1(),,Tn()OuiOui=0=3

Mon idée était de simuler des données normalement distribuées approximativement et de tester l'algorithme à ce sujet. Ensuite, testez l'algorithme sur chaque jeu de données transformé , pour voir à quel point la sortie change.OuiT1(Y),,Tn(y)

Notez que je ne contrôle pas la distribution des simulés , je ne peux donc pas les simuler à l'aide d'une distribution qui généralise le Normal (telle que la distribution des erreurs généralisées asymétriques).Y

Matteo Fasiolo
la source
2
Le problème avec une séquence de transformations comme celle-là est que votre conclusion se limite aux effets de cette séquence particulière. Votre séquence en effet un chemin dans l' espace correspondant à une seule famille de distributions basée sur une transformation (vraisemblablement à un paramètre, puisque vous dites "séquence") de la normale. Donner que la région viable est 2D et que pour tout point donné à l'intérieur il y a un nombre infini de distributions différentes, regarder une seule famille tracer une seule courbe serait quelque peu limitant ... (ctd )( γ 1 , γ 2 )(γ1,γ2)(γ1,γ2)
Glen_b -Reinstate Monica
1
(ctd) ... surtout si la famille particulière que vous générez n'a pas tendance à révéler des problèmes qui pourraient autrement être assez courants.
Glen_b -Reinstate Monica

Réponses:

22

Cela peut être fait en utilisant la transformation sinh-arcsinh de

Jones, MC et Pewsey A. (2009). Distributions Sinh-arcsinh . Biometrika 96: 761–780.

La transformation est définie comme

()H(X;ϵ,δ)=sinh[δsinh-1(X)-ϵ],

et δ R + . Lorsque cette transformation est appliquée à la CDF normale S ( x ; ϵ , δ ) = Φ [ H ( x ; ϵ , δ ) ] , elle produit une distribution unimodale dont les paramètres ( ϵ , δ ) contrôlent respectivement l'asymétrie et la kurtosis (Jones et Pewsey, 2009), au sens de van Zwet (1969) . De plus, si ϵ = 0 et δϵRδR+S(X;ϵ,δ)=Φ[H(X;ϵ,δ)](ϵ,δ)ϵ=0 , on obtient la distribution normale d'origine. Voir le code R suivant.δ=1

fs = function(x,epsilon,delta) dnorm(sinh(delta*asinh(x)-epsilon))*delta*cosh(delta*asinh(x)-epsilon)/sqrt(1+x^2)

vec = seq(-15,15,0.001)

plot(vec,fs(vec,0,1),type="l")
points(vec,fs(vec,1,1),type="l",col="red")
points(vec,fs(vec,2,1),type="l",col="blue")
points(vec,fs(vec,-1,1),type="l",col="red")
points(vec,fs(vec,-2,1),type="l",col="blue")

vec = seq(-5,5,0.001)

plot(vec,fs(vec,0,0.5),type="l",ylim=c(0,1))
points(vec,fs(vec,0,0.75),type="l",col="red")
points(vec,fs(vec,0,1),type="l",col="blue")
points(vec,fs(vec,0,1.25),type="l",col="red")
points(vec,fs(vec,0,1.5),type="l",col="blue")

Par conséquent, en choisissant une séquence appropriée de paramètres , vous pouvez générer une séquence de distributions / transformations avec différents niveaux d'asymétrie et de kurtosis et les rendre aussi similaires ou différents de la distribution normale que vous le souhaitez.(ϵn,δn)

Le graphique suivant montre le résultat produit par le code R. Pour (i) et δ = 1 , et (ii) ϵ = 0 et δ = ( 0,5 , 0,75 , 1 , 1,25 , 1,5 ) .ϵ=(-2,-1,0,1,2)δ=1 ϵ=0δ=(0,5,0,75,1,1,25,1,5)

entrez la description de l'image ici

entrez la description de l'image ici

La simulation de cette distribution est simple étant donné qu'il suffit de transformer un échantillon normal en utilisant l'inverse de .()

H-1(X;ϵ,δ)=sinh[δ-1(sinh-1(X)+ϵ)]

la source
2
Merci beaucoup Procrastinator! Ceci est exactement ce que je cherchais.
Matteo Fasiolo
2
Il semble que gamlss.dist::rSHASHoces distributions puissent être générées.
Artem Klevtsov,
7

Cela peut être fait en utilisant des variables / distributions aléatoires Lambert W x F. Une variable aléatoire Lambert W x F (RV) est un X non transformé linéairement (RV) de distribution F.

α=1Gaussianize()

Ils sont mis en œuvre dans le

Les transformations Lambert W x F se déclinent en 3 saveurs:

  • type = 's'γR
  • type = 'h'δ0α
  • asymétrique et à queue lourde (type = 'hh'δl,δr0

Voir les références sur les queues asymétriques et lourdes (Avertissement: je suis l'auteur.)

Dans R, vous pouvez simuler, estimer, tracer, etc. plusieurs distributions Lambert W x F avec le package LambertW .

library(LambertW)
library(RColorBrewer)
# several heavy-tail parameters
delta.v <- seq(0, 2, length = 11)
x.grid <- seq(-5, 5, length = 100)
col.v <- colorRampPalette(c("black", "orange"))(length(delta.v))

plot(x.grid, dnorm(x.grid), lwd = 2, type = "l", col = col.v[1],
     ylab = "")
for (ii in seq_along(delta.v)) {
  lines(x.grid, dLambertW(x.grid, "normal", 
                          theta = list(delta = delta.v[ii], beta = c(0, 1))),
        col = col.v[ii])
}
legend("topleft", paste(delta.v), col = col.v, lty = 1,
       title = "delta = ")

entrez la description de l'image ici

γδlδr

Georg M. Goerg
la source
5

Une telle séquence est l'exponentiation à divers degrés. Par exemple

library(moments)
x <- rnorm(1000) #Normal data
x2 <- 2^x #One transformation
x3 <- 2^{x^2} #A stronger transformation
test <- cbind(x, x2, x3) 
apply(test, 2, skewness) #Skewness for the three distributions
apply(test, 2, kurtosis) #Kurtosis for the three distributions

X1.1,X1.2X2

Peter Flom - Réintégrer Monica
la source
0

Même réponse que @ user10525 mais en python

import numpy as np
from scipy.stats import norm
def sinh_archsinh_transformation(x,epsilon,delta):
    return norm.pdf(np.sinh(delta*np.arcsinh(x)-epsilon))*delta*np.cosh(delta*np.arcsinh(x)-epsilon)/np.sqrt(1+np.power(x,2))


vec = np.arange(start=-15,stop=15+0.001,step=0.001)

import matplotlib.pyplot as plt
plt.plot(vec,sinh_archsinh_transformation(vec,0,1))
plt.plot(vec,sinh_archsinh_transformation(vec,1,1),color='red')
plt.plot(vec,sinh_archsinh_transformation(vec,2,1),color='blue')
plt.plot(vec,sinh_archsinh_transformation(vec,-1,1),color='red')
plt.plot(vec,sinh_archsinh_transformation(vec,-2,1),color='blue')

[1]

JPlatts
la source