遗传算法与Java代码简单实现
参阅地址:
https://www.jianshu.com/p/ae5157c26af9
代码实现:
- public class GA {
- private int ChrNum = 10; //染色体数量
- private String[] ipop = new String[ChrNum]; //一个种群中染色体总数
- private int generation = 0; //染色体代号
- public static final int GENE = 46; //基因数
- private double bestfitness = Double.MAX_VALUE; //函数最优解
- private int bestgenerations; //所有子代与父代中最好的染色体
- private String beststr; //最优解的染色体的二进制码
- /**
- * 初始化一条染色体(用二进制字符串表示)
- */
- private String initChr() {
- String res = "";
- for (int i = 0; i < GENE; i++) {
- if (Math.random() > 0.5) {
- res += "0";
- } else {
- res += "1";
- }
- }
- return res;
- }
- /**
- * 初始化一个种群(10条染色体)
- */
- private String[] initPop() {
- String[] ipop = new String[ChrNum];
- for (int i = 0; i < ChrNum; i++) {
- ipop[i] = initChr();
- }
- return ipop;
- }
- /**
- * 将染色体转换成x,y变量的值
- */
- private double[] calculatefitnessvalue(String str) {
- //二进制数前23位为x的二进制字符串,后23位为y的二进制字符串
- int a = Integer.parseInt(str.substring(0, 23), 2);
- int b = Integer.parseInt(str.substring(23, 46), 2);
- double x = a * (6.0 - 0) / (Math.pow(2, 23) - 1); //x的基因
- double y = b * (6.0 - 0) / (Math.pow(2, 23) - 1); //y的基因
- //需优化的函数
- double fitness = 3 - Math.sin(2 * x) * Math.sin(2 * x)
- - Math.sin(2 * y) * Math.sin(2 * y);
- double[] returns = { x, y, fitness };
- return returns;
- }
- /**
- * 轮盘选择
- * 计算群体上每个个体的适应度值;
- * 按由个体适应度值所决定的某个规则选择将进入下一代的个体;
- */
- private void select() {
- double evals[] = new double[ChrNum]; // 所有染色体适应值
- double p[] = new double[ChrNum]; // 各染色体选择概率
- double q[] = new double[ChrNum]; // 累计概率
- double F = 0; // 累计适应值总和
- for (int i = 0; i < ChrNum; i++) {
- evals[i] = calculatefitnessvalue(ipop[i])[2];
- if (evals[i] < bestfitness){ // 记录下种群中的最小值,即最优解
- bestfitness = evals[i];
- bestgenerations = generation;
- beststr = ipop[i];
- }
- F = F + evals[i]; // 所有染色体适应值总和
- }
- for (int i = 0; i < ChrNum; i++) {
- p[i] = evals[i] / F;
- if (i == 0)
- q[i] = p[i];
- else {
- q[i] = q[i - 1] + p[i];
- }
- }
- for (int i = 0; i < ChrNum; i++) {
- double r = Math.random();
- if (r <= q[0]) {
- ipop[i] = ipop[0];
- } else {
- for (int j = 1; j < ChrNum; j++) {
- if (r < q[j]) {
- ipop[i] = ipop[j];
- }
- }
- }
- }
- }
- /**
- * 交叉操作 交叉率为60%,平均为60%的染色体进行交叉
- */
- private void cross() {
- String temp1, temp2;
- for (int i = 0; i < ChrNum; i++) {
- if (Math.random() < 0.60) {
- int pos = (int)(Math.random()*GENE)+1; //pos位点前后二进制串交叉
- temp1 = ipop[i].substring(0, pos) + ipop[(i + 1) % ChrNum].substring(pos);
- temp2 = ipop[(i + 1) % ChrNum].substring(0, pos) + ipop[i].substring(pos);
- ipop[i] = temp1;
- ipop[(i + 1) / ChrNum] = temp2;
- }
- }
- }
- /**
- * 基因突变操作 1%基因变异
- */
- private void mutation() {
- for (int i = 0; i < 4; i++) {
- int num = (int) (Math.random() * GENE * ChrNum + 1);
- int chromosomeNum = (int) (num / GENE) + 1; // 染色体号
- int mutationNum = num - (chromosomeNum - 1) * GENE; // 基因号
- if (mutationNum == 0)
- mutationNum = 1;
- chromosomeNum = chromosomeNum - 1;
- if (chromosomeNum >= ChrNum)
- chromosomeNum = 9;
- String temp;
- String a; //记录变异位点变异后的编码
- if (ipop[chromosomeNum].charAt(mutationNum - 1) == '0') { //当变异位点为0时
- a = "1";
- } else {
- a = "0";
- }
- //当变异位点在首、中段和尾时的突变情况
- if (mutationNum == 1) {
- temp = a + ipop[chromosomeNum].substring(mutationNum);
- } else {
- if (mutationNum != GENE) {
- temp = ipop[chromosomeNum].substring(0, mutationNum -1) + a
- + ipop[chromosomeNum].substring(mutationNum);
- } else {
- temp = ipop[chromosomeNum].substring(0, mutationNum - 1) + a;
- }
- }
- //记录下变异后的染色体
- ipop[chromosomeNum] = temp;
- }
- }
- public static void main(String args[]) {
- GA Tryer = new GA();
- Tryer.ipop = Tryer.initPop(); //产生初始种群
- String str = "";
- //迭代次数
- for (int i = 0; i < 1000000; i++) {
- Tryer.select();
- Tryer.cross();
- Tryer.mutation();
- Tryer.generation = i;
- }
- double[] x = Tryer.calculatefitnessvalue(Tryer.beststr);
- str = "最小值" + Tryer.bestfitness + '\n' + "第"
- + Tryer.bestgenerations + "个染色体:<" + Tryer.beststr + ">" + '\n'
- + "x=" + x[0] + '\n' + "y=" + x[1];
- System.out.println(str);
- }
- }
遗传算法与Java代码简单实现的更多相关文章
- java代码简单练习
总结: package com.ds; import java.awt.Color; import java.awt.FlowLayout; import javax.swing.JFrame; im ...
- Java代码 简单用于处理和数据库相关的操作
package util; import org.apache.commons.beanutils.BeanUtils; import java.lang.reflect.InvocationTarg ...
- java代码简单实现队列
1. 基于链表简单实现 import lombok.AllArgsConstructor; import lombok.Data; import lombok.NoArgsConstructor; / ...
- java代码简单实现栈
1. 基于数组简单实现 /** * @author <a herf="mailto:yanwu0527@163.com">XuBaofeng</a> * @ ...
- Centos7.4简单安装使用gitlab+maven+jenkins实现java代码的持续集成部署
1.工具的简单介绍 gitlab--源代码版本管理控制工具 maven--java代码编译构建工具 jenkins--基于java开发的自动化持续集成部署工具 sonar--代码质量管理工具 2.gi ...
- Java静态检测工具/Java代码规范和质量检查简单介绍(转)
静态检查: 静态测试包括代码检查.静态结构分析.代码质量度量等.它可以由人工进行,充分发挥人的逻辑思维优势,也可以借助软件工具自动进行.代码检查代码检查包括代码走查.桌面检查.代码审查等,主要检查代码 ...
- MongoDB最简单的入门教程之三 使用Java代码往MongoDB里插入数据
前两篇教程我们介绍了如何搭建MongoDB的本地环境: MongoDB最简单的入门教程之一 环境搭建 以及如何用nodejs读取MongoDB里的记录: MongoDB最简单的入门教程之二 使用nod ...
- 几种简单的负载均衡算法及其Java代码实现
什么是负载均衡 负载均衡,英文名称为Load Balance,指由多台服务器以对称的方式组成一个服务器集合,每台服务器都具有等价的地位,都可以单独对外提供服务而无须其他服务器的辅助.通过某种负载分担技 ...
- Jmeter4.0---- jmeter中写入java代码_简单了解(15)
1.说明 BeanShell:是一个小型嵌入式Java源代码解释器,具有对象脚本语言特性,能够动态地执行标准JAVA语法,并利用在JavaScript和Perl中常见的的松散类型.命令.闭包等通用脚本 ...
随机推荐
- Vbox中多台虚拟机搭建简单子网
一.目标拓扑结构: 要使192.168.31.1和192.168.32.1互相ping通. 二.步骤及问题: 1.路由器配置 SEED_Router配置IP并开启路由转发协议: ifconfig et ...
- PHP json_encode函数的参数说明
PHP json_encode函数的参数说明 一.总结 一句话总结: · json_encode常常被用于将数组转换成json格式的字符串来表示,但是json_encode的第一个参数却并不一定是数组 ...
- 10分钟梳理MySQL核心知识点
数据库的使用,是开发人员的基本功,对它掌握越清晰越深入,你能做的事情就越多. 做业务,要懂基本的SQL语句:做性能优化,要懂索引,懂引擎:做分库分表,要懂主从,懂读写分离... 今天我们用10分钟,重 ...
- CentOS 上 Jenkins 的安装
Jenkins 的前身是 Hudson. Jenkins 是一款开源 CI&CD 软件,用于自动化各种任务,包括构建.测试和部署软件. Jenkins 支持各种运行方式,可通过系统包.Dock ...
- 数据库 | Oracle数据库查表空间使用情况
平时在使用Oracle的时候,如果业务中的数据量激增.数据量变大,很有可能就会有表空间不足的情况,需要重点关注.今天我们分享下如何查看表空间的使用情况. 一.如何查看使用状况 我们废话不说,先直接贴上 ...
- 前端知识点回顾——Javascript篇(三)
数组的冒泡.选择和插入排序法 冒泡排序法(从小到大) function bubble(arr){ for(let i = 0 ;i<arr.length-1;i++){ for(let j = ...
- 使用预设半透明鼠标Cursor
using System;using System.Collections.Generic;using System.ComponentModel;using System.Data;using Sy ...
- ubuntu下如何关闭某个端口?
1. 开启防火墙 sudo ufw enable 2. 关闭某个端口,如80端口 sudo ufw deny 80 3. 查询当前防火墙状态 sudo ufw status
- ObjectAnimator属性动画示例代码
import android.animation.AnimatorSet; import android.animation.ObjectAnimator; import android.app.Ac ...
- Ubuntu14.04+安卓系统4.3+JDK6编译源码
本博客主要参照: https://www.jianshu.com/p/ecb9c132030f https://blog.csdn.net/gobitan/article/details/243674 ...