吉布斯采样给出了小概率

时间:2017-03-14 14:16:31

标签: machine-learning probability markov-chains simulated-annealing markov-random-fields

作为我们最终设计项目的一部分,我们必须设计一个Gibbs采样器来对图像进行去噪。我们选择使用Metropolis算法而不是常规的Gibbs采样器。该算法的粗略草图如下,所有像素均为0-255灰度值。此外,我们使用简单的先验分布平滑。

main()
    get input image as img
    originalImg = img
    for k = 1 to 1000
        beta = 3/log(1+k)
        initialEnergy = energy(img,originalImg)
        for i = 0 to imageRows
            for j = 0 to imageCols
                img[i][j] = metropolisSample(beta,originalImg,img,initialEnergy,i,j)


energy(img,originalImg)
    for i = 1 to imageRows
        for j = 1 to imageCols
            ans += (img[i][j] - originalImg[i][j])^2 / (255*255)
            ans += (img[i][j] - image[i][j+1])^2 / (255*255)
            ans += (img[i][j] - image[i][j-1])^2 / (255*255)
            ans += (img[i][j] - image[i+1][j])^2 / (255*255)
            ans += (img[i][j] - image[i-1][j])^2 / (255*255)
    return ans


metropolisSample(beta,originalImg,img,initialEnergy,i,j)
    imageCopy = img
    imageCopy[i][j] = random int between 0 and 255
    newEnergy = energy(imageCopy,originalImg)
    if (newEnergy < initialEnergy)
        initialEnergy = newEnergy
        return imageCopy[i][j]
    else
        rand = random float between 0 and 1 
        prob = exp(-(1/beta) * (newEnergy - initialEnergy))
        if rand < prob
            initialEnergy = newEnergy
            return imageCopy[i][j]
        else
            return img[i][j]

这几乎是该计划的要点。我的问题在于我计算概率的步骤

prob = exp(-(1/beta) * (newEnergy - initialEnergy))

能量的差异很大,概率几乎总是为零。减轻这种情况的正确方法是什么?我们也尝试过Gibbs采样方法,但我们遇到了类似的问题。 Gibbs采样器代码如下。我们不使用metropolisSample,而是使用gibbsSample

gibbsSample(beta,originalImg,img,initialEnergy,i,j)
    imageCopy = img
    sum = 0
    for k = 0 to 255
        imageCopy[i][j] = k
        energies[k] = energy(imageCopy,originalImg)
        prob[k] = exp(-(1/beta) * energies[k])
        sum += prob[k]

    for k = 0 to 255
        prob[k] / sum

    for k = 1 to 255
        prob[k] = prob[k-1] + prob[k] //Convert our PDF to a CDF

    rand = random float between 0 and 1
    k = 0
    while (1)
        if (rand < prob[k])
            break
        k++
    initialEnergy = energy[k]
    return k

我们也遇到了类似的问题。当我们计算

prob[k] = exp(-(1/beta) * energies[k])

我们的能量如此之大,以至于我们的概率都变为零。从理论上讲,这不应该是一个问题,因为我们将它们全部加起来然后除以总和,但浮点表示只是不够准确。什么是解决这个问题的好方法?

2 个答案:

答案 0 :(得分:1)

我对你的具体问题一无所知,但我的第一反应是扩大能量。您的像素范围为0..255,这是任意的。如果像素是0到1之间的分数,则结果会有很大差异。

如果能量单位在像素^ 2中,请尝试将能量除以256 ^ 2。否则,请尝试除以256。

另外,鉴于数据是完全随机的,有可能存在非常高的能量,实际上应该没有很高的概率。

我对你的问题缺乏了解可能导致一个无用的答案。如果是这样,请忽略它。

答案 1 :(得分:0)

我认为在伊辛模型中进行吉布斯抽样的概率应该是

p = 1 / (1 + np.exp(-2 * beta * Energy(x,y)))