基于生物地理学的优化算法(BBO)(基础篇)
📘

基于生物地理学的优化算法(BBO)(基础篇)

第 1/3 篇

BBO 算法在 MT5 里的实现骨架

生物地理学优化(BBO)把种群栖息地当作「适宜度」载体,用迁移率与物种生存率迭代寻优,本质是一类受生态机制启发的全局搜索器。在 MT5 中把它接进 Expert Advisor,主要工作量落在适应度函数的定义与栖息地变量的周期更新上。 Andrey Dik 在 2026 年 6 月 22 日发布的实现版本,截至发文被查看 175 次、零评论,说明这套思路在零售交易者圈子里还偏冷门。冷门不代表无效——BBO 对多峰代价函数往往比网格搜索更省评估次数,这对 MT5 回测调用次数受限的环境是直接利好。 落地时先确认两件事:一是把 K 线序列与指标缓冲接成 double 数组喂给栖息地适应度;二是限制最大迁移代数,避免策略测试器里单次优化跑穿数小时。开 MT5 新建 EA,把下面这段栖息地初始化逻辑粘进 OnInit 做验证,能跑通即说明你的编译器环境兼容 BBO 结构体。

MQL5 / C++
class="kw">struct Habitat {
   class="type">class="kw">double vars[];      class=class="str">"cmt">// 栖息地物种变量(待优化参数向量)
   class="type">class="kw">double fitness;     class=class="str">"cmt">// 适应度值,越低代表越优
   class="type">class="kw">double immigration; class=class="str">"cmt">// 迁入率
   class="type">class="kw">double emigration;  class=class="str">"cmt">// 迁出率
};
Habitat g_habitat[class="num">50]; class=class="str">"cmt">// 全局栖息地种群,规模 class="num">50

「BBO 怎么从群岛迁徙里长出来」

  • 年丹·西蒙把生物地理学里的物种分布模型搬进了优化算法,起名 BBO。它和遗传算法借遗传学、神经网络仿神经元一个路数,核心数学来自 20 世纪 60 年代就成型的栖息地物种分布描述。

自然界里 HSI 高的岛物种多、往外迁得快;条件差的岛物种少、往里迁得多。BBO 就拿这套迁入迁出动态当交换解特征的机制,变异概率直接由物种分布模型算,不靠拍脑袋。 优质解会主动把特征共享出去,自己又不容易被随机改掉——这是它最显眼的一个性质,后面写代码时你能直接看到这类解在种群里被保护的逻辑。外汇和贵金属参数优化用这类算法仍属高风险,回测漂亮不代表实盘能复现。

◍ 把群岛模型塞进 BBO 类的骨架里

BBO 把寻优过程映射成群岛生态:50 座岛 = 50 个可行解,栖息地适宜度 HSI 高就是好解。劣质岛物种少、迁入率高,会不断吸优质岛的特征;优质岛饱和后迁出率高,向外共享变量。算法里前 2 个精英解(自然保护区)不参与迁移和变异,避免把搜到的最优解弄丢。 落地到 MT5 的 C_AO_BBO 类,它继承自 C_AO 基类,默认种群规模 50、最大迁入率 I=1.0、最大迁出率 E=1.0、基础变异概率 0.01、精英保留 2、最大物种数 50。构造函数给这些 BBO 专属参数赋初值,SetParams() 用外部参数数组改值,不用动父类封装的优化底座。 Init() 做内存分配与概率归一化,Moving() 跑主循环:按 HSI 排序 → 算每个岛的物种数 Si = Smax×(N-rank_i)/N、迁入率 λi = I×(1-Si/Smax)、迁出率 μi = E×(Si/Smax) → 非精英岛按 λi 概率从轮盘赌选中的高 μ 源岛抄变量 → 非精英岛按 m_rate = m×(1-probability) 变异。Revision() 只干一件事:扫一遍种群,把优于 fB 的个体刷新进最优解变量。 InitializePopulation 用 u.RNDfromCI 在 rangeMin~rangeMax 内撒点,再按 rangeStep 用 SeInDiSp 就近取整,保证解落在离散合法网格;CalculateRates 用线性模型让物种数与适应度成正比,生存概率查表,超 Smax 直接置 0。Migration 跳过精英、按迁入率改坐标、按迁出率轮盘赌选源;Mutation 与生存概率反比,极优(HSI=95)和极劣(HSI=5)突变率高、中等(HSI=50)低,外汇/贵金属参数寻优属高风险实验,上 MT5 跑前先拿历史数据回测这套迁移率公式。

用高斯曲线给栖息地适宜度打分

CalculateProbability 方法按物种数量估算栖息地生存概率:当数量落在 speciesMax/2 这个均衡中点附近时概率最高,越往两端偏,概率沿高斯曲线陡降。也就是说,物种数严重偏离均衡值的栖息地,其适宜度会明显低于接近中点的那些。 这套建模把生物多样性压成了一个简化却高效的“适宜度”指标,方便后续在优化器里直接比较不同栖息地。你在 MT5 里把 speciesMax 从 50 调到 100,中点就移到 25,概率峰位会整体平移,可用历史品种参数回测观察分布变化。 外汇与贵金属市场波动剧烈、杠杆风险高,任何基于此类模型的参数映射都只是概率倾向,实盘前务必用策略测试器验证。

MQL5 / C++
class=class="str">"cmt">//——————————————————————————————————————————————————————————————————————————————
class C_AO_BBO : class="kw">public C_AO
{
  class="kw">public: class=class="str">"cmt">//--------------------------------------------------------------------
  ~C_AO_BBO() { }
  C_AO_BBO()
  {
    ao_name = "BBO";
    ao_desc = "Biogeography-Based Optimization";
    ao_link = "[MQL5官方文档]
    popSize       = class="num">50;      class=class="str">"cmt">// population size(number of habitats)
    immigrationMax = class="num">1.0;    class=class="str">"cmt">// maximum immigration rate
    emigrationMax  = class="num">1.0;    class=class="str">"cmt">// maximum emigration rate
    mutationProb   = class="num">0.5;    class=class="str">"cmt">// mutation probability
    elitismCount   = class="num">2;      class=class="str">"cmt">// number of elite solutions
    speciesMax     = class="num">50;     class=class="str">"cmt">// maximum number of species
    ArrayResize(params, class="num">6);
    params [class="num">0].name = "popSize";       params [class="num">0].val = popSize;
    params [class="num">1].name = "immigrationMax"; params [class="num">1].val = immigrationMax;
    params [class="num">2].name = "emigrationMax";  params [class="num">2].val = emigrationMax;
    params [class="num">3].name = "mutationProb";   params [class="num">3].val = mutationProb;
    params [class="num">4].name = "elitismCount";   params [class="num">4].val = elitismCount;
    params [class="num">5].name = "speciesMax";     params [class="num">5].val = speciesMax;
  }
  class="type">void SetParams()
  {
    popSize       = (class="type">int)params [class="num">0].val;
    immigrationMax = params      [class="num">1].val;
    emigrationMax  = params      [class="num">2].val;
    mutationProb   = params      [class="num">3].val;
    elitismCount   = (class="type">int)params [class="num">4].val;
    speciesMax     = (class="type">int)params [class="num">5].val;
  }
  class="type">bool Init(const class="type">class="kw">double &rangeMinP  [],  class=class="str">"cmt">// minimum values
             const class="type">class="kw">double &rangeMaxP  [],  class=class="str">"cmt">// maximum values
             const class="type">class="kw">double &rangeStepP [],  class=class="str">"cmt">// step change
             const class="type">int     epochsP = class="num">0);   class=class="str">"cmt">// number of epochs
  class="type">void Moving();
  class="type">void Revision();
  class=class="str">"cmt">//----------------------------------------------------------------------------
  class="type">class="kw">double immigrationMax;   class=class="str">"cmt">// maximum immigration rate

常见问题

把每个候选解当成一个岛屿,适宜度高的岛会向外「移民」特征,适宜度低的岛接收「移民」变异,多代迭代后群体整体更优。先用纸面跑 10 代看分布变化再写代码。
用高斯曲线按变量离历史最优区的距离打分,中心高、边缘低,连续可微。把 sigma 设成变量范围的 1/6 起步,再按回测调。
小布可读取你关注的贵金属或外汇品种页,用类 BBO 的群体评估给出参数敏感区提示,省去自己搭骨架。打开对应品种页即可看到 AIGC 诊断。
迁徙率没随代数衰减、精英岛没保留是主因。骨架里给 top 10% 岛加保护位,迁移率每代乘 0.95 试试。
sigma 过大所有岛分数接近,优化退化成随机搜;过小只认极窄区,易早熟。先用变量跨度除 6,回测 50 代看收敛曲线再动。