metropolis算法的简单c++实现以及matlab实现

metropolis是一种采样方法,一般用于获取某些拥有某些比较复杂的概率分布的样本。

1.采样最基本的是随机数的生成,一般是生成具有均匀分布的随机数,比如C++里面的rand函数,可以直接采用。

2.采样复杂一点是转化发,用于生成普通常见的分布,如高斯分布,它的一般是通过对均匀分布或者现有分布的转化形成,如高斯分布就可以通过如下方法生成:

令:U,V为均匀分布的随即变量;

那么:Gauss=sqrt(-2lnU)cos(2*pi*V)。

(详细参照Box-Muller)

像这种高斯分布matelab可以直接用randN生成。

3. 最后一种方法是类MCMC方法,其实MCMC是一种架构,这里我们说一种最简单的Metropolis方法,它的核心思想是构建马尔克夫链,该链上每一个节点都成为一个样本,利用马尔克夫链的转移和接受概率,以一定的方式对样本进行生成,这个方法简单有效,具体可以参考《LDA数学八卦》的,里面都已经进行了详细的介绍。本文给一个小demo,是利用C++写的。例外代码的matlab版本也有,但不是我写的,一并贴出来,matlab的画图功能可以视觉化的验证采样有效性,(好像matlab有个小bug),

待生成样本的概率分布为:pow(t,-3.5)*exp(-1/(2*t)) (csdn有没有想latex那种编辑方式啊??),这里在metropolis中假设马尔克夫链是symmetric,就是p(x|y)=p(y|x),整个代码如下:

#include <iostream>
#include <time.h>
#include <stdlib.h>
#include <cmath>
using namespace std;

#define debug(A) std::cout<<#A<<": "<<A<<std::endl;

class MCMCSimulation{

	public:
		int N;
		int nn;
		float* sample;

		MCMCSimulation(){

			this->N=1000;
			this->nn=0.1*N;
			this->sample=new float[N];
			this->sample[0]=0.3;

		}

		void run(){

			for (int i=1;i<this->N;i++){

				float p_sample=this->PDF_proposal(3);	

				float alpha=PDF(p_sample)/PDF(this->sample[i-1]);

				if(PDF_proposal(1) < this->min(alpha,1)){

					this->sample[i]=p_sample;

				}else{

					this->sample[i]=this->sample[i-1];

				}
				//debug(p_sample);
				//debug(PDF_proposal(1));
				//debug(sample[i]);
				cout<<sample[i]<<endl;
			}

		}
	private:

		//the probability desity function
		float PDF(float t){

			return pow(t,-3.5)*exp(-1/(2*t));	

		} 

		//generate a rand number from 0-MAX, with a specified precision
		float PDF_proposal(int MAX){

			//srand
			return (float)(MAX)*(float)(rand())/(float)(RAND_MAX);

		}

		float min(float x, float y){

			if(x<y){

				return x; 

			}else{

				return y;
			}

		}

};

int main(){

	MCMCSimulation* sim =new MCMCSimulation();
	sim->run();
	delete sim;
	return 1;
}

matlab版本

%% Simple Metropolis algorithm example
%{
---------------------------------------------------------------------------
*Created by:                  Date:            Comment:
 Felipe Uribe-Castillo        July 2011        Final project algorithm
*Mail:
 [email protected]
*University:
 National university of Colombia at Manizales. Civil Engineering Dept.
---------------------------------------------------------------------------
The Metropolis algorithm:
First MCMC to obtain samples from some complex probability distribution
and to integrate very complex functions by random sampling.
It considers only symmetric proposals (proposal pdf). 

Original contribution:
-"The Monte Carlo method"
  Metropolis & Ulam (1949).
-"Equations of State Calculations by Fast Computing Machines"
  Metropolis, Rosenbluth, Rosenbluth, Teller & Teller (1953).
---------------------------------------------------------------------------
Based on:
1."Markov chain Monte Carlo and Gibbs sampling"
   B.Walsh ----- Lecture notes for EEB 581, version april 2004.
   http://web.mit.edu/~wingated/www/introductions/mcmc-gibbs-intro.pdf
%}
clear; close all; home; format long g;

%% Initial data
% Distributions
nu           = 5;                                       % Target PDF parameter
p            = @(t) (t.^(-nu/2-1)).*(exp(-1./(2*t)));   % Target "PDF", Ref. 1 - Ex. 2
proposal_PDF = @(mu) unifrnd(0,3);                      % Proposal PDF
% Parameters
N        = 1000;              % Number of samples (iterations)
nn       = 0.1*(N);           % Number of samples for examine the AutoCorr
theta    = zeros(1,N);        % Samples drawn form the target "PDF"
theta(1) = 0.3;               % Initial state of the chain

%% Procedure
for i = 1:N
   theta_ast = proposal_PDF([]);          % Sampling from the proposal PDF
   alpha     = p(theta_ast)/p(theta(i));  % Ratio of the density at theta_ast and theta points
   if rand <= min(alpha,1)
      % Accept the sample with prob = min(alpha,1)
      theta(i+1) = theta_ast;
   else
      % Reject the sample with prob = 1 - min(alpha,1)
      theta(i+1) = theta(i);
   end
end

% Autocorrelation (AC)
pp = theta(1:nn);   pp2 = theta(end-nn:end);   % First ans Last nn samples
[r lags]   = xcorr(pp-mean(pp), 'coeff');
[r2 lags2] = xcorr(pp2-mean(pp2), 'coeff');

%% Plots
% Autocorrelation
figure;
subplot(2,1,1);   stem(lags,r);
title('Autocorrelation', 'FontSize', 14);
ylabel('AC (first samples)', 'FontSize', 12);
subplot(2,1,2);   stem(lags2,r2);
ylabel('AC (last samples)', 'FontSize', 12);

% Samples and distributions
xx = eps:0.01:10;   % x-axis (Graphs)
figure;
% Histogram and target dist
subplot(2,1,1);
[n1 x1] = hist(theta, ceil(sqrt(N)));
bar(x1,n1/(N*(x1(2)-x1(1))));   colormap summer;   hold on;   % Normalized histogram
plot(xx, p(xx)/trapz(xx,p(xx)), 'r-', 'LineWidth', 3);        % Normalized function
grid on;   xlim([0 max(theta)]);
title('Distribution of samples', 'FontSize', 14);
ylabel('Probability density function', 'FontSize', 12);
% Samples
subplot(2,1,2);
plot(theta, 1:N+1, 'b-');   xlim([0 max(theta)]);   ylim([0 N]);   grid on;
xlabel('Location', 'FontSize', 12);
ylabel('Iterations, N', 'FontSize', 12); 

%%End

下面是样本的分布图

时间: 2024-10-28 12:11:08

metropolis算法的简单c++实现以及matlab实现的相关文章

C# 实现寻峰算法的简单优化(包含边峰,最小峰值,峰距)

原文:C# 实现寻峰算法的简单优化(包含边峰,最小峰值,峰距) 核心寻峰算法的原理参考Ronny,链接:投影曲线的波峰查找, C#翻译原理代码参考sowhat4999,链接:C#翻译Matlab中findpeaks方法 前人种树,后人乘凉.感谢原作者详细的解释说明. 这里先把翻译代码贴一下(略微的修改了sowhat4999代码中的几个参数) //调用方法 List<double> data = new List<double>{25, 8, 15, 5, 6, 10, 10, 3,

1101: 零起点学算法08——简单的输入和计算(a+b)

1101: 零起点学算法08--简单的输入和计算(a+b) Time Limit: 1 Sec  Memory Limit: 128 MB   64bit IO Format: %lldSubmitted: 3669  Accepted: 1997[Submit][Status][Web Board] Description 前面7道题做下来,对输出和计算有点感觉了吧? 不过很可惜的是前面的做法,好像太死了,写了一个计算3+4的程序,计算5+6又得改程序,计算机真的只能这么实现,那么我们比计算机

【机器学习算法-python实现】采样算法的简单实现

1.背景 采样算法是机器学习中比较常用,也比较容易实现的(出去分层采样).常用的采样算法有以下几种(来自百度知道): 一.单纯随机抽样(simple random sampling) 将调查总体全部观察单位编号,再用抽签法或随机数字表随机抽取部分观察单位组成样本. 优点:操作简单,均数.率及相应的标准误计算简单. 缺点:总体较大时,难以一一编号. 二.系统抽样(systematic sampling) 又称机械抽样.等距抽样,即先将总体的观察单位按某一顺序号分成n个部分,再从第一部分随机抽取第k

机器学习&amp;数据挖掘笔记_16(常见面试之机器学习算法思想简单梳理)

http://www.cnblogs.com/tornadomeet/p/3395593.html 机器学习&数据挖掘笔记_16(常见面试之机器学习算法思想简单梳理) 前言: 找工作时(IT行业),除了常见的软件开发以外,机器学习岗位也可以当作是一个选择,不少计算机方向的研究生都会接触这个,如果你的研究方向是机器学习/数据挖掘之类,且又对其非常感兴趣的话,可以考虑考虑该岗位,毕竟在机器智能没达到人类水平之前,机器学习可以作为一种重要手段,而随着科技的不断发展,相信这方面的人才需求也会越来越大.

【算法】简单选择排序C语言实现

上一篇我们谈到了冒泡排序,实现了两个版本的冒泡排序,不知道大家有没有对冒泡排序的特点进行一下总结呢?其实冒泡排序还算是比较暴力的,因为它频繁不断的进行交换,那么这样的话,我们的计算机的计算频率就会很高,不算是很高效,那么我们可不可以找到一种交换次数少一点的方法呢?这就引出了我们接下来要介绍的简单选择排序算法了. 简单选择排序的基本思想就是通过N-1次的关键字间的比较,从N - i + 1个记录中选择一个关键字最小记录,并和第i(1<= i <= n)个记录交换,其实简单选择排序和冒泡排序在思路

约瑟夫问题 算法很简单保证每隔人都能看懂用数组实现 利用循环删除数组中的元素

#include<iostream> using namespace std; const int size = 1000; void ArrDel() { int arr[size]; //循环结束标志,一直循环到数组中只剩下最后一个元素结束 int currentNum = size; int count = 0; for (int k = 0; k < size; k++) { arr[k] = k; } //currentNum==1表示数组中只剩下最后一个元素 是循环结束的标志

A*算法最简单的介绍

A*搜寻算法,俗称A星算法,作为启发式搜索算法中的一种,这是一种在图形平面上,有多个节点的路径,求出最低通过成本的算法.常用于游戏中的NPC的移动计算,或线上游戏的BOT的移动计算上.该算法像Dijkstra算法一样,可以找到一条最短路径:也像BFS一样,进行启发式的搜索. A*算法最为核心的部分,就在于它的一个估值函数的设计上:        f(n)=g(n)+h(n) 其中f(n)是每个可能试探点的估值,它有两部分组成:    一部分,为g(n),它表示从起始搜索点到当前点的代价(通常用某

编程实现哈希存储算法的简单实例

编程实现哈希存储算法的简单实现实例. 通过编写一个简单的哈希实例来加强对哈希算法的理解.下面实例包括存储与查找算法.拉链法解决冲突问题. 如果时间长了对哈希算法的理论知识不够了解,可以先阅读前面转载的两篇文档: 字符串哈希到整数函数,算法:http://blog.csdn.net/hzhsan/article/details/25552153 Hash算法冲突解决方法分析:http://blog.csdn.net/hzhsan/article/details/25555127 // 假设现在要实

[转]算法的简单归类。大数据常用算法

无论是机器学习.模式识别.数据挖掘.统计学习.计算机视觉.语音识别.自然语言处理都涉及到算法. 1.树:决策树(Decision Tree)是在已知各种情况发生概率的基础上,通过构成决策树来求取净现值的期望值大于等于零的概率,评价项目风险,判断其可行性的决策分析方法,是直观运用概率分析的一种图解法.由于这种决策分支画成图形很像一棵树的枝干,故称决策树.在机器学习中,决策树是一个预测模型,他代表的是对象属性与对象值之间的一种映射关系.Entropy = 系统的凌乱程度,使用算法ID3, C4.5和