简体   繁体   中英

How to generate iid sample from a given arbitrary probability density function

I want a function randgen(f, N) in python to generate N sample from a given pdf.

It's what I wrote:

import numpy as np
import matplotlib.pyplot as plt

def randgen(f,N, M=1):
    sample = M*np.random.random(N)
    y=[]
    sum = 0
    for x in sample:
      v = f(x);
      sum+=v;
      y.append(v)
    y = y/sum;
    return np.random.choice(sample, p=y, size=N)

def pp(x):
  return x**2

z = randgen(pp, 2000)
plt.hist(z)

It generates the following histogram for the function y=x^2 . It seems working.

在此处输入图片说明

I have seen similar questions but without a clear reference to the function definition for randgen(f,N) which can takes arbitrary functions. I would like to know if my approach is correct or I missed a point.

Okay, to unpack your solution:

  • generate N random numbers between 0 and 1
  • calculate a probability for each number depending on a given function
  • rescale your solution so that the integral of that function is 1
  • draw N numbers from your "generated" pdf

The way you did it definitely fulfills the criteria for a probability density function and your solution should be correct, but can improve it by using uniformly spaced numbers for the calcultation of your pdf.

numpy.linspace(start,stop,N) produces N evenly spaced numbers between start and stop. ( https://docs.scipy.org/doc/numpy/reference/generated/numpy.linspace.html )

Your solution is fine for discrete pdfs if you apply my suggested addition instead of your
sample = M*np.random.random(N)
sample = np.linspace(start, stop, N)

edit: The pdf also has a requirement, that the probabilities have to be positive, so there should be some mechanisms included to avoid negative function values for x in range [0,1].

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM