C语言的萤火虫智能算法实现

来源:http://www.cnblogs.com/javado/archive/2013/05/19/3087765.html


--算法说明:荧火虫算法

-- ================================初始化开始================================
domx = { { -1, 2 }, { -1, 2 } }; -- 定义域
rho = 0.4 --荧光素挥发因子
gamma = 0.6 -- 适应度提取比例
beta = 0.08 -- 邻域变化率
nt = 5 -- 邻域阀值(邻域荧火虫数)
s = 0.3 -- 步长
s1 = 0.03 -- 局部最优扰动
iot0 = 5 -- 荧光素浓度
rs = 1.5 -- 感知半径
r0 = 1.5 -- 决策半径
-- ================================初始化结束================================


-- ===============================分配空间开始===============================
m = 2 -- 解空间维数
n = 30 -- 群规模
gaddress = {} -- 分配荧火虫地址空间
gvalue = {} -- 分配适应度存放空间
ioti = {} -- 分配荧光素存放空间
rdi = {} -- 分配荧火虫决策半径存放空间
-- ===============================分配空间结束===============================




-- ===================================函数===================================
sin = math.sin
sqrt = math.sqrt
pi = math.pi
random = math.random


-- 求解函数
function maxfun(x)
    return 4 - (x[1] * sin( 4 * pi * x[1]) - x[2] * sin(4 * pi * x[2] + pi + 1))
end


-- 求2范数 维数相关
function norm(xi, xj)
    return sqrt((xi[1] - xj[1]) ^ 2 + (xi[2] - xj[2]) ^ 2)
end


print(maxfun({1.88, 1.81}))
print(maxfun({1.8506610777502, 1.8685277417146})) -- 6.8987454465589




-- ===========================荧火虫常量初始化开始============================
math.randomseed(os.time())


-- 初始化个体
for i = 1, n do
    gaddress[i] = {}
    for j = 1, m do
        gaddress[i][j] = domx[j][1] + (domx[j][2] - domx[j][1]) * random()
    end
end


-- 初始化荧光素
for i = 1, n do
    ioti[i] = iot0
end




-- 初始化决策半径
for i = 1, n do
    rdi[i] = r0
end
-- ===========================荧火虫常量初始化结束============================




-- =============================iter_max迭代开始=============================


-- 最大迭代次数
iter_max = 20


for iter = 1, iter_max do


    -- 下面我加了一个变异操作
    j = 1
    for i = 1, n do
        gvalue[i] = maxfun(gaddress[i])
        if gvalue[j] > gvalue[i] then
            j = i
        end
    end


    for k = 1, m do
        gaddress[j][k] = domx[k][1] + (domx[k][2] - domx[k][1]) * random()
    end
    gvalue[j] = maxfun(gaddress[j])
    


    -- 更新荧光素
    for i = 1, n do
        ioti[i] = (1 - rho) * ioti[i] + gamma * gvalue[i]
    end


    -- 各荧火虫移动过程开始
    for i = 1, n do
        -- 决策半径内找更优点
        Nit = {} -- 存放荧火虫序号
        for j = 1, n do
            if j ~= i and ioti[i] < ioti[j] and norm(gaddress[j], gaddress[i]) < rdi[i] then
                table.insert(Nit, j)
            end
        end


        -- 找下一步移动的点开始
        Nitnum = #Nit
        if Nitnum > 0 then
            
            -- 选出Nit荧光素之差及差的总和
            Nitioti = {}
            Denominator = 0
            for k = 1, Nitnum do
                Nitioti[k] = ioti[Nit[k]] - ioti[i]
                Denominator = Denominator + Nitioti[k]
            end


            -- 求出各个选择概率
            Nitioti[1] = Nitioti[1] / Denominator
            for k = 2, Nitnum do
                Nitioti[k] = Nitioti[k] / Denominator + Nitioti[k - 1]
            end


            -- 轮盘赌
            rand = random()
            idx = 1
            for k = 1, Nitnum do
                if rand < Nitioti[k] then
                    idx = Nit[k]
                    break
                end
            end


            -- 移动
            dist = norm(gaddress[idx], gaddress[i])
            for k = 1, m do
                gaddress[i][k] = gaddress[i][k] + s * (gaddress[idx][k] - gaddress[i][k]) / dist
                if gaddress[i][k] < domx[k][1] then
                    gaddress[i][k] = domx[k][1]
                elseif gaddress[i][k] > domx[k][2] then
                    gaddress[i][k] = domx[k][2]
                end
            end


            -- 更新决策半径
            rdi[i] = rdi[i] + beta * (nt - Nitnum)
            if rdi[i] < 0 then
                rdi[i] = 0
            elseif rdi[i] > rs then
                rdi[i] = rs
            end
        else
            for k = 1, m do
                gaddress[i][k] = gaddress[i][k] + s1 * (random() - 0.5) * (domx[k][2] - domx[k][1])
                if gaddress[i][k] < domx[k][1] then
                    gaddress[i][k] = domx[k][1]
                elseif gaddress[i][k] > domx[k][2] then
                    gaddress[i][k] = domx[k][2]
                end
            end
        end
    end
end


-- =============================iter_max迭代结束=============================






-- =============================输出最优结果开始=============================


-- 求各个荧火虫的值
j = 1
for i = 1, m do
    gvalue[i] = maxfun(gaddress[i])
    if gvalue[i] < gvalue[j] then
        j = i
    end
end


-- 最大值
BestAddress = gaddress[j]
print("(" .. BestAddress[1] .. ", " .. BestAddress[2] .. ")\t" .. gvalue[j])
-- =============================输出最优结果结束=============================

你可能感兴趣的:(人工生命,科学计算,人工智能,算法)